Update repository sharing actions [SCI-6918]

This commit is contained in:
Oleksii Kriuchykhin 2022-07-01 11:55:27 +02:00
parent 3fbc5af9a1
commit 17178c28d5
8 changed files with 69 additions and 47 deletions

View file

@ -490,7 +490,7 @@ class RepositoriesController < ApplicationController
end
def check_share_permissions
render_403 if !can_share_repository?(@repository) || current_user.teams.count <= 1
render_403 unless can_share_repository?(@repository)
end
def repository_params

View file

@ -6,11 +6,11 @@ class TeamRepositoriesController < ApplicationController
# DELETE :team_id/repositories/:repository_id/team_repositories/:id
def destroy
team_repository = @repository.team_repositories.find_by_id(destory_params[:id])
team_shared_object = @repository.team_shared_objects.find_by(id: destory_params[:id])
if team_repository
log_activity(:unshare_inventory, team_repository)
team_repository.destroy
if team_shared_object
log_activity(:unshare_inventory, team_shared_object)
team_shared_object.destroy!
render json: {}, status: :no_content
else
render json: { message: I18n.t('repositories.multiple_share_service.nothing_to_delete') },
@ -89,14 +89,14 @@ class TeamRepositoriesController < ApplicationController
}
end
def log_activity(type_of, team_repository)
def log_activity(type_of, team_shared_object)
Activities::CreateActivityService
.call(activity_type: type_of,
owner: current_user,
subject: team_repository.repository,
subject: team_shared_object.shared_repository,
team: current_team,
message_items: { repository: team_repository.repository.id,
team: team_repository.team.id,
message_items: { repository: team_shared_object.shared_repository.id,
team: team_shared_object.team.id,
permission_level:
Extends::SHARED_INVENTORIES_PL_MAPPINGS[team_repository.permission_level.to_sym] })
end

View file

@ -24,9 +24,11 @@ module PermissionCheckableModel
def load_user_role_permissions(user)
if user_assignments.loaded?
user_assignments.detect { |user_assignment| user_assignment.user == user }&.user_role&.permissions
user_assignments.detect do |user_assignment|
user_assignment.user == user && user_assignment.team == user.current_team
end&.user_role&.permissions
else
user_assignments.find_by(user: user)&.user_role&.permissions
user_assignments.find_by(user: user, team: user.current_team)&.user_role&.permissions
end
end
end

View file

@ -42,11 +42,11 @@ class Repository < RepositoryBase
scope :archived, -> { where(archived: true) }
scope :accessible_by_teams, lambda { |teams|
accessible_repositories = left_outer_joins(:team_repositories)
accessible_repositories = left_outer_joins(:team_shared_objects)
accessible_repositories =
accessible_repositories
.where(team: teams)
.or(accessible_repositories.where(team_repositories: { team: teams }))
.or(accessible_repositories.where(team_shared_objects: { team: teams }))
.or(accessible_repositories
.where(permission_level: [Extends::SHARED_INVENTORIES_PERMISSION_LEVELS[:shared_read],
Extends::SHARED_INVENTORIES_PERMISSION_LEVELS[:shared_write]]))
@ -126,7 +126,7 @@ class Repository < RepositoryBase
end
def shared_with_anybody?
(!not_shared? || team_repositories.any?)
(!not_shared? || team_shared_objects.any?)
end
def shared_with?(team)
@ -144,15 +144,15 @@ class Repository < RepositoryBase
def shared_with_read?(team)
return false if self.team == team
shared_read? || team_repositories.where(team: team, permission_level: :shared_read).any?
shared_read? || team_shared_objects.where(team: team, permission_level: :shared_read).any?
end
def private_shared_with?(team)
team_repositories.where(team: team).any?
team_shared_objects.where(team: team).any?
end
def private_shared_with_write?(team)
team_repositories.where(team: team, permission_level: :shared_write).any?
team_shared_objects.where(team: team, permission_level: :shared_write).any?
end
def self.viewable_by_user(_user, teams)

View file

@ -3,18 +3,22 @@
class TeamSharedObject < ApplicationRecord
enum permission_level: Extends::SHARED_OBJECTS_PERMISSION_LEVELS.except(:not_shared)
after_create :assign_shared_inventories, if: -> { shared_object.is_a?(Repository) }
before_destroy :unassign_unshared_items, if: -> { shared_object.is_a?(Repository) }
before_destroy :unassign_unshared_inventories, if: -> { shared_object.is_a?(Repository) }
belongs_to :team
belongs_to :shared_object, polymorphic: true
belongs_to :shared_object, polymorphic: true, inverse_of: :team_shared_objects
belongs_to :shared_repository,
(lambda do |team_shared_object|
team_shared_object.shared_object_type == 'RepositoryBAse' ? self : none
team_shared_object.shared_object_type == 'RepositoryBase' ? self : none
end),
optional: true, foreign_key: :shared_object_id, inverse_of: :team_shared_object
before_destroy :unassign_unshared_items, if: -> { shared_object.is_a?(Repository) }
optional: true,
class_name: 'RepositoryBase',
foreign_key: :shared_object_id
validates :permission_level, presence: true
validates :shared_object, uniqueness: { scope: :team_id }
validates :shared_object_type, uniqueness: { scope: %i(shared_object_id team_id) }
validate :team_cannot_be_the_same
private
@ -23,13 +27,30 @@ class TeamSharedObject < ApplicationRecord
errors.add(:team_id, :same_team) if shared_object.team.id == team_id
end
def assign_shared_inventories
viewer_role = UserRole.find_by(name: UserRole.public_send('viewer_role').name)
normal_user_role = UserRole.find_by(name: UserRole.public_send('normal_user_role').name)
team.users.find_each do |user|
shared_object.user_assignments.create!(
user: user,
user_role: shared_write? ? normal_user_role : viewer_role,
team: team
)
end
end
def unassign_unshared_items
return if repository.shared_read? || repository.shared_write?
return if shared_object.shared_read? || shared_object.shared_write?
MyModuleRepositoryRow.joins(my_module: { experiment: { project: :team } })
.joins(repository_row: :repository)
.where(my_module: { experiment: { projects: { team: team } } })
.where(repository_rows: { repository: repository })
.where(repository_rows: { repository: shared_object })
.destroy_all
end
def unassign_unshared_inventories
team.repository_sharing_user_assignments.where(assignable: shared_object).find_each(&:destroy!)
end
end

View file

@ -33,18 +33,17 @@ module Repositories
if !@shared_with_all.nil? && !@shared_permission_level.nil?
old_permission_level = @repository.permission_level
@repository.permission_level = @shared_with_all ? @shared_permission_level : :not_shared
if @repository.changed?
log_activity_share_all(@repository.permission_level, old_permission_level, @repository) if @repository.save
if @repository.changed? && @repository.save
log_activity_share_all(@repository.permission_level, old_permission_level, @repository)
end
end
@team_ids_for_share.each do |share|
team_repository = TeamRepository.new(repository: @repository,
team_id: share[:id],
permission_level: share[:permission_level])
team_shared_object =
@repository.team_shared_objects.new(team_id: share[:id], permission_level: share[:permission_level])
if team_repository.save
log_activity(:share_inventory, team_repository)
if team_shared_object.save
log_activity(:share_inventory, team_shared_object)
else
warnings << I18n.t('repositories.multiple_share_service.unable_to_share',
repository: @repository.name, team: share[:id])
@ -52,11 +51,11 @@ module Repositories
end
@team_ids_for_unshare.each do |team_id|
team_repository = TeamRepository.where(repository: @repository, team_id: team_id).first
team_shared_object = @repository.team_shared_objects.find_by(team_id: team_id)
if team_repository
log_activity(:unshare_inventory, team_repository)
team_repository.destroy
if team_shared_object
log_activity(:unshare_inventory, team_shared_object)
team_shared_object.destroy!
else
warnings << I18n.t('repositories.multiple_share_service.unable_to_unshare',
repository: @repository.name, team: team_id)
@ -64,11 +63,11 @@ module Repositories
end
@team_ids_for_update.each do |update|
team_repository = TeamRepository.where(repository: @repository, team_id: update[:id]).first
team_repository.permission_level = update[:permission_level] if team_repository
team_shared_object = @repository.team_shared_objects.find_by(team_id: update[:id])
team_shared_object.permission_level = update[:permission_level] if team_shared_object
if team_repository&.save
log_activity(:update_share_inventory, team_repository)
if team_shared_object&.save
log_activity(:update_share_inventory, team_shared_object)
else
warnings << I18n.t('repositories.multiple_share_service.unable_to_update',
repository: @repository.name, team: update[:id])
@ -98,16 +97,16 @@ module Repositories
true
end
def log_activity(type_of, team_repository)
def log_activity(type_of, team_shared_object)
Activities::CreateActivityService
.call(activity_type: type_of,
owner: @user,
subject: team_repository.repository,
subject: team_shared_object.shared_object,
team: @team,
message_items: { repository: team_repository.repository.id,
team: team_repository.team.id,
message_items: { repository: team_shared_object.shared_object.id,
team: team_shared_object.team.id,
permission_level:
Extends::SHARED_INVENTORIES_PL_MAPPINGS[team_repository.permission_level.to_sym] })
Extends::SHARED_INVENTORIES_PL_MAPPINGS[team_shared_object.permission_level.to_sym] })
end
def log_activity_share_all(permission_level, old_permission_level, repository)

View file

@ -49,7 +49,7 @@
</div>
<div class="repo-datatables-buttons">
<div class="share-repository-button" data-view-mode="active">
<% if can_share_repository?(@repository) && current_user.teams.count > 1 %>
<% if can_share_repository?(@repository) %>
<%= link_to team_repository_share_modal_path(current_team, repository_id: @repository),
class: 'btn btn-light share-repo-option', remote: true, id: 'shareRepoBtn' do %>
<span class="fas fa-user-plus"></span>

View file

@ -77,7 +77,7 @@ class AddTeamLevelPermissions < ActiveRecord::Migration[6.1]
@viewer_role.permissions = @viewer_role.permissions - VIEWER_PERMISSIONS
@viewer_role.save(validate: false)
UserAssignment.where(assignable_type: %w(Team Protocol Report Repository)).delete_all
UserAssignment.where(assignable_type: %w(Team Protocol Report RepositoryBase)).delete_all
end
end
end