Merge pull request #4183 from okriuchykhin/ok_SCI_6917

Convert team_repository to polymorphic relation [SCI-6917]
This commit is contained in:
Alex Kriuchykhin 2022-08-31 16:43:35 +02:00 committed by GitHub
commit e23475fbbe
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
10 changed files with 117 additions and 86 deletions

View file

@ -20,8 +20,8 @@ class Repository < RepositoryBase
class_name: 'User',
inverse_of: :restored_repositories,
optional: true
has_many :team_repositories, inverse_of: :repository, dependent: :destroy
has_many :teams_shared_with, through: :team_repositories, source: :team
has_many :team_shared_objects, as: :shared_object, dependent: :destroy
has_many :teams_shared_with, through: :team_shared_objects, source: :team
has_many :repository_snapshots,
class_name: 'RepositorySnapshot',
foreign_key: :parent_id,

View file

@ -48,7 +48,12 @@ class Team < ApplicationRecord
has_many :reports, inverse_of: :team, dependent: :destroy
has_many :activities, inverse_of: :team, dependent: :destroy
has_many :assets, inverse_of: :team, dependent: :destroy
has_many :team_repositories, inverse_of: :team, dependent: :destroy
has_many :team_shared_objects, inverse_of: :team, dependent: :destroy
has_many :team_shared_repositories,
-> { where(shared_object_type: 'RepositoryBase') },
class_name: 'TeamSharedObject',
inverse_of: :team
has_many :shared_repositories, through: :team_shared_objects, source: :shared_object, source_type: 'RepositoryBase'
has_many :repository_sharing_user_assignments,
(lambda do |team|
joins(
@ -59,7 +64,7 @@ class Team < ApplicationRecord
.where.not('user_assignments.team_id = repositories.team_id')
end),
class_name: 'UserAssignment'
has_many :shared_repositories,
has_many :shared_by_user_repositories,
through: :repository_sharing_user_assignments,
source: :assignable,
source_type: 'RepositoryBase'

View file

@ -1,30 +0,0 @@
# frozen_string_literal: true
class TeamRepository < ApplicationRecord
enum permission_level: Extends::SHARED_INVENTORIES_PERMISSION_LEVELS.except(:not_shared)
belongs_to :team
belongs_to :repository
before_destroy :unassign_unshared_items
validates :permission_level, presence: true
validates :repository, uniqueness: { scope: :team_id }
validate :team_cannot_be_the_same
private
def team_cannot_be_the_same
errors.add(:team_id, :same_team) if repository&.team_id == team_id
end
def unassign_unshared_items
return if repository.shared_read? || repository.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 })
.destroy_all
end
end

View file

@ -0,0 +1,35 @@
# frozen_string_literal: true
class TeamSharedObject < ApplicationRecord
enum permission_level: Extends::SHARED_OBJECTS_PERMISSION_LEVELS
belongs_to :team
belongs_to :shared_object, polymorphic: true
belongs_to :shared_repository,
(lambda do |team_shared_object|
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) }
validates :permission_level, presence: true
validates :shared_object, uniqueness: { scope: :team_id }
validate :team_cannot_be_the_same
private
def team_cannot_be_the_same
errors.add(:team_id, :same_team) if shared_object.team.id == team_id
end
def unassign_unshared_items
return if repository.shared_read? || repository.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 })
.destroy_all
end
end

View file

@ -18,12 +18,15 @@ class UserAssignment < ApplicationRecord
private
def assign_shared_inventories
assignable.repository_sharing_user_assignments
.select('DISTINCT assignable_id, user_assignments.*')
.find_each do |repository_sharing_user_assignment|
new_user_assignment = repository_sharing_user_assignment.dup
new_user_assignment.assign_attributes(user: user)
new_user_assignment.save!
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)
assignable.team_shared_repositories.find_each do |team_shared_repository|
assignable.repository_sharing_user_assignments.create!(
user: user,
user_role: team_shared_repository.shared_write? ? normal_user_role : viewer_role,
assignable: team_shared_repository.shared_object
)
end
end

View file

@ -409,6 +409,11 @@ class Extends
shared_write: 2
}.freeze
SHARED_OBJECTS_PERMISSION_LEVELS = {
shared_read: 1,
shared_write: 2
}.freeze
SHARED_INVENTORIES_PL_MAPPINGS = {
shared_read: 'view-only',
shared_write: 'edit'

View file

@ -1,6 +1,13 @@
# frozen_string_literal: true
class MigrateSharedRepositoriesToUserAssignments < ActiveRecord::Migration[6.1]
class TeamRepository < ApplicationRecord
self.table_name = 'team_repositories'
enum permission_level: { not_shared: 0, shared_read: 1, shared_write: 2 }
belongs_to :team
belongs_to :repository
end
def up
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)
@ -23,9 +30,34 @@ class MigrateSharedRepositoriesToUserAssignments < ActiveRecord::Migration[6.1]
UserAssignment.import(user_assignments)
end
end
remove_index :repositories, :permission_level
remove_index :team_repositories, :permission_level
remove_index :team_repositories, :repository_id
remove_index :team_repositories, %i(team_id repository_id), unique: true
rename_table :team_repositories, :team_shared_objects
rename_column :team_shared_objects, :repository_id, :shared_object_id
add_column :team_shared_objects, :shared_object_type, :string
execute("UPDATE team_shared_objects SET shared_object_type = 'RepositoryBase'")
add_index :team_shared_objects,
%i(shared_object_type shared_object_id team_id),
name: 'index_team_shared_objects_on_shared_type_and_id_and_team_id',
unique: true
end
def down
remove_index :team_shared_objects,
%i(shared_object_type shared_object_id team_id),
name: 'index_team_shared_objects_on_shared_type_and_id_and_team_id',
unique: true
remove_column :team_shared_objects, :shared_object_type
rename_column :team_shared_objects, :shared_object_id, :repository_id
rename_table :team_shared_objects, :team_repositories
add_index :team_repositories, %i(team_id repository_id), unique: true
add_index :team_repositories, :repository_id
add_index :team_repositories, :permission_level
add_index :repositories, :permission_level
UserAssignment.joins("INNER JOIN repositories ON user_assignments.assignable_id = repositories.id "\
"AND user_assignments.assignable_type = 'RepositoryBase' "\
"AND user_assignments.team_id != repositories.team_id")

View file

@ -2669,24 +2669,25 @@ ALTER SEQUENCE public.tags_id_seq OWNED BY public.tags.id;
--
-- Name: team_repositories; Type: TABLE; Schema: public; Owner: -
-- Name: team_shared_objects; Type: TABLE; Schema: public; Owner: -
--
CREATE TABLE public.team_repositories (
CREATE TABLE public.team_shared_objects (
id bigint NOT NULL,
team_id bigint,
repository_id bigint,
shared_object_id bigint,
permission_level integer DEFAULT 0 NOT NULL,
created_at timestamp without time zone NOT NULL,
updated_at timestamp without time zone NOT NULL
updated_at timestamp without time zone NOT NULL,
shared_object_type character varying
);
--
-- Name: team_repositories_id_seq; Type: SEQUENCE; Schema: public; Owner: -
-- Name: team_shared_objects_id_seq; Type: SEQUENCE; Schema: public; Owner: -
--
CREATE SEQUENCE public.team_repositories_id_seq
CREATE SEQUENCE public.team_shared_objects_id_seq
START WITH 1
INCREMENT BY 1
NO MINVALUE
@ -2695,10 +2696,10 @@ CREATE SEQUENCE public.team_repositories_id_seq
--
-- Name: team_repositories_id_seq; Type: SEQUENCE OWNED BY; Schema: public; Owner: -
-- Name: team_shared_objects_id_seq; Type: SEQUENCE OWNED BY; Schema: public; Owner: -
--
ALTER SEQUENCE public.team_repositories_id_seq OWNED BY public.team_repositories.id;
ALTER SEQUENCE public.team_shared_objects_id_seq OWNED BY public.team_shared_objects.id;
--
@ -3850,10 +3851,10 @@ ALTER TABLE ONLY public.tags ALTER COLUMN id SET DEFAULT nextval('public.tags_id
--
-- Name: team_repositories id; Type: DEFAULT; Schema: public; Owner: -
-- Name: team_shared_objects id; Type: DEFAULT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.team_repositories ALTER COLUMN id SET DEFAULT nextval('public.team_repositories_id_seq'::regclass);
ALTER TABLE ONLY public.team_shared_objects ALTER COLUMN id SET DEFAULT nextval('public.team_shared_objects_id_seq'::regclass);
--
@ -4574,11 +4575,11 @@ ALTER TABLE ONLY public.tags
--
-- Name: team_repositories team_repositories_pkey; Type: CONSTRAINT; Schema: public; Owner: -
-- Name: team_shared_objects team_shared_objects_pkey; Type: CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.team_repositories
ADD CONSTRAINT team_repositories_pkey PRIMARY KEY (id);
ALTER TABLE ONLY public.team_shared_objects
ADD CONSTRAINT team_shared_objects_pkey PRIMARY KEY (id);
--
@ -5657,13 +5658,6 @@ CREATE INDEX index_repositories_on_discarded_at ON public.repositories USING btr
CREATE INDEX index_repositories_on_my_module_id ON public.repositories USING btree (my_module_id);
--
-- Name: index_repositories_on_permission_level; Type: INDEX; Schema: public; Owner: -
--
CREATE INDEX index_repositories_on_permission_level ON public.repositories USING btree (permission_level);
--
-- Name: index_repositories_on_restored_by_id; Type: INDEX; Schema: public; Owner: -
--
@ -6393,31 +6387,17 @@ CREATE INDEX index_tags_on_project_id ON public.tags USING btree (project_id);
--
-- Name: index_team_repositories_on_permission_level; Type: INDEX; Schema: public; Owner: -
-- Name: index_team_shared_objects_on_shared_type_and_id_and_team_id; Type: INDEX; Schema: public; Owner: -
--
CREATE INDEX index_team_repositories_on_permission_level ON public.team_repositories USING btree (permission_level);
CREATE UNIQUE INDEX index_team_shared_objects_on_shared_type_and_id_and_team_id ON public.team_shared_objects USING btree (shared_object_type, shared_object_id, team_id);
--
-- Name: index_team_repositories_on_repository_id; Type: INDEX; Schema: public; Owner: -
-- Name: index_team_shared_objects_on_team_id; Type: INDEX; Schema: public; Owner: -
--
CREATE INDEX index_team_repositories_on_repository_id ON public.team_repositories USING btree (repository_id);
--
-- Name: index_team_repositories_on_team_id; Type: INDEX; Schema: public; Owner: -
--
CREATE INDEX index_team_repositories_on_team_id ON public.team_repositories USING btree (team_id);
--
-- Name: index_team_repositories_on_team_id_and_repository_id; Type: INDEX; Schema: public; Owner: -
--
CREATE UNIQUE INDEX index_team_repositories_on_team_id_and_repository_id ON public.team_repositories USING btree (team_id, repository_id);
CREATE INDEX index_team_shared_objects_on_team_id ON public.team_shared_objects USING btree (team_id);
--
@ -6868,11 +6848,11 @@ ALTER TABLE ONLY public.tables
--
-- Name: team_repositories fk_rails_15daa6a6bf; Type: FK CONSTRAINT; Schema: public; Owner: -
-- Name: team_shared_objects fk_rails_15daa6a6bf; Type: FK CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.team_repositories
ADD CONSTRAINT fk_rails_15daa6a6bf FOREIGN KEY (repository_id) REFERENCES public.repositories(id);
ALTER TABLE ONLY public.team_shared_objects
ADD CONSTRAINT fk_rails_15daa6a6bf FOREIGN KEY (shared_object_id) REFERENCES public.repositories(id);
--
@ -8124,10 +8104,10 @@ ALTER TABLE ONLY public.tags
--
-- Name: team_repositories fk_rails_f99472b670; Type: FK CONSTRAINT; Schema: public; Owner: -
-- Name: team_shared_objects fk_rails_f99472b670; Type: FK CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.team_repositories
ALTER TABLE ONLY public.team_shared_objects
ADD CONSTRAINT fk_rails_f99472b670 FOREIGN KEY (team_id) REFERENCES public.teams(id);
@ -8388,6 +8368,7 @@ INSERT INTO "schema_migrations" (version) VALUES
('20220325101011'),
('20220328164215'),
('20220516111152'),
('20220621153016');
('20220621153016'),
('20220624091046');

View file

@ -27,7 +27,7 @@ describe Repository, type: :model do
it { should have_many :repository_rows }
it { should have_many :repository_table_states }
it { should have_many :report_elements }
it { should have_many(:team_repositories).dependent(:destroy) }
it { should have_many(:team_shared_objects).dependent(:destroy) }
it { should have_many(:teams_shared_with) }
end

View file

@ -34,7 +34,7 @@ describe Team, type: :model do
it { should have_many :tiny_mce_assets }
it { should have_many :repositories }
it { should have_many :reports }
it { should have_many(:team_repositories).dependent(:destroy) }
it { should have_many(:team_shared_objects).dependent(:destroy) }
it { should have_many :shared_repositories }
end