diff options
Diffstat (limited to 'app/finders')
-rw-r--r-- | app/finders/contributed_projects_finder.rb | 24 | ||||
-rw-r--r-- | app/finders/group_projects_finder.rb | 42 | ||||
-rw-r--r-- | app/finders/groups_finder.rb | 18 | ||||
-rw-r--r-- | app/finders/issuable_finder.rb | 29 | ||||
-rw-r--r-- | app/finders/issues_finder.rb | 6 | ||||
-rw-r--r-- | app/finders/joined_groups_finder.rb | 24 | ||||
-rw-r--r-- | app/finders/personal_projects_finder.rb | 28 | ||||
-rw-r--r-- | app/finders/projects_finder.rb | 72 | ||||
-rw-r--r-- | app/finders/snippets_finder.rb | 6 | ||||
-rw-r--r-- | app/finders/union_finder.rb | 11 |
10 files changed, 143 insertions, 117 deletions
diff --git a/app/finders/contributed_projects_finder.rb b/app/finders/contributed_projects_finder.rb index 0209649b017..a685719555c 100644 --- a/app/finders/contributed_projects_finder.rb +++ b/app/finders/contributed_projects_finder.rb @@ -1,4 +1,4 @@ -class ContributedProjectsFinder +class ContributedProjectsFinder < UnionFinder def initialize(user) @user = user end @@ -11,27 +11,19 @@ class ContributedProjectsFinder # # Returns an ActiveRecord::Relation. def execute(current_user = nil) - if current_user - relation = projects_visible_to_user(current_user) - else - relation = public_projects - end + segments = all_projects(current_user) - relation.includes(:namespace).order_id_desc + find_union(segments, Project).includes(:namespace).order_id_desc end private - def projects_visible_to_user(current_user) - authorized = @user.contributed_projects.visible_to_user(current_user) + def all_projects(current_user) + projects = [] - union = Gitlab::SQL::Union. - new([authorized.select(:id), public_projects.select(:id)]) + projects << @user.contributed_projects.visible_to_user(current_user) if current_user + projects << @user.contributed_projects.public_to_user(current_user) - Project.where("projects.id IN (#{union.to_sql})") - end - - def public_projects - @user.contributed_projects.public_only + projects end end diff --git a/app/finders/group_projects_finder.rb b/app/finders/group_projects_finder.rb new file mode 100644 index 00000000000..3b9a421b118 --- /dev/null +++ b/app/finders/group_projects_finder.rb @@ -0,0 +1,42 @@ +class GroupProjectsFinder < UnionFinder + def initialize(group, options = {}) + @group = group + @options = options + end + + def execute(current_user = nil) + segments = group_projects(current_user) + find_union(segments, Project) + end + + private + + def group_projects(current_user) + only_owned = @options.fetch(:only_owned, false) + only_shared = @options.fetch(:only_shared, false) + + projects = [] + + if current_user + if @group.users.include?(current_user) + projects << @group.projects unless only_shared + projects << @group.shared_projects unless only_owned + else + unless only_shared + projects << @group.projects.visible_to_user(current_user) + projects << @group.projects.public_to_user(current_user) + end + + unless only_owned + projects << @group.shared_projects.visible_to_user(current_user) + projects << @group.shared_projects.public_to_user(current_user) + end + end + else + projects << @group.projects.public_only unless only_shared + projects << @group.shared_projects.public_only unless only_owned + end + + projects + end +end diff --git a/app/finders/groups_finder.rb b/app/finders/groups_finder.rb new file mode 100644 index 00000000000..4e43f42e9e1 --- /dev/null +++ b/app/finders/groups_finder.rb @@ -0,0 +1,18 @@ +class GroupsFinder < UnionFinder + def execute(current_user = nil) + segments = all_groups(current_user) + + find_union(segments, Group).order_id_desc + end + + private + + def all_groups(current_user) + groups = [] + + groups << current_user.authorized_groups if current_user + groups << Group.unscoped.public_to_user(current_user) + + groups + end +end diff --git a/app/finders/issuable_finder.rb b/app/finders/issuable_finder.rb index f7240edd618..046286dd9e1 100644 --- a/app/finders/issuable_finder.rb +++ b/app/finders/issuable_finder.rb @@ -80,9 +80,10 @@ class IssuableFinder @projects = project elsif current_user && params[:authorized_only].presence && !current_user_related? @projects = current_user.authorized_projects.reorder(nil) + elsif group + @projects = GroupProjectsFinder.new(group).execute(current_user).reorder(nil) else - @projects = ProjectsFinder.new.execute(current_user, group: group). - reorder(nil) + @projects = ProjectsFinder.new.execute(current_user).reorder(nil) end end @@ -171,14 +172,12 @@ class IssuableFinder def by_scope(items) case params[:scope] - when 'created-by-me', 'authored' then + when 'created-by-me', 'authored' items.where(author_id: current_user.id) - when 'all' then - items - when 'assigned-to-me' then + when 'assigned-to-me' items.where(assignee_id: current_user.id) else - raise 'You must specify default scope' + items end end @@ -198,8 +197,7 @@ class IssuableFinder end def by_group(items) - items = items.of_group(group) if group - + # Selection by group is already covered by `by_project` and `projects` items end @@ -244,10 +242,17 @@ class IssuableFinder items end + def filter_by_upcoming_milestone? + params[:milestone_title] == '#upcoming' + end + def by_milestone(items) if milestones? if filter_by_no_milestone? items = items.where(milestone_id: [-1, nil]) + elsif filter_by_upcoming_milestone? + upcoming = Milestone.where(project_id: projects).upcoming + items = items.joins(:milestone).where(milestones: { title: upcoming.title }) else items = items.joins(:milestone).where(milestones: { title: params[:milestone_title] }) @@ -263,11 +268,9 @@ class IssuableFinder def by_label(items) if labels? if filter_by_no_label? - items = items. - joins("LEFT OUTER JOIN label_links ON label_links.target_type = '#{klass.name}' AND label_links.target_id = #{klass.table_name}.id"). - where(label_links: { id: nil }) + items = items.without_label else - items = items.joins(:labels).where(labels: { title: label_names }) + items = items.with_label(label_names) if projects items = items.where(labels: { project_id: projects }) diff --git a/app/finders/issues_finder.rb b/app/finders/issues_finder.rb index 20a2b0ce8f0..c2befa5a5b3 100644 --- a/app/finders/issues_finder.rb +++ b/app/finders/issues_finder.rb @@ -19,4 +19,10 @@ class IssuesFinder < IssuableFinder def klass Issue end + + private + + def init_collection + Issue.visible_to_user(current_user) + end end diff --git a/app/finders/joined_groups_finder.rb b/app/finders/joined_groups_finder.rb new file mode 100644 index 00000000000..47174980258 --- /dev/null +++ b/app/finders/joined_groups_finder.rb @@ -0,0 +1,24 @@ +class JoinedGroupsFinder < UnionFinder + def initialize(user) + @user = user + end + + # Finds the groups of the source user, optionally limited to those visible to + # the current user. + def execute(current_user = nil) + segments = all_groups(current_user) + + find_union(segments, Group).order_id_desc + end + + private + + def all_groups(current_user) + groups = [] + + groups << @user.authorized_groups.visible_to_user(current_user) if current_user + groups << @user.authorized_groups.public_to_user(current_user) + + groups + end +end diff --git a/app/finders/personal_projects_finder.rb b/app/finders/personal_projects_finder.rb index a61ffa22990..3ad4bd5f066 100644 --- a/app/finders/personal_projects_finder.rb +++ b/app/finders/personal_projects_finder.rb @@ -1,4 +1,4 @@ -class PersonalProjectsFinder +class PersonalProjectsFinder < UnionFinder def initialize(user) @user = user end @@ -11,31 +11,19 @@ class PersonalProjectsFinder # # Returns an ActiveRecord::Relation. def execute(current_user = nil) - if current_user - relation = projects_visible_to_user(current_user) - else - relation = public_projects - end + segments = all_projects(current_user) - relation.includes(:namespace).order_id_desc + find_union(segments, Project).includes(:namespace).order_id_desc end private - def projects_visible_to_user(current_user) - authorized = @user.personal_projects.visible_to_user(current_user) + def all_projects(current_user) + projects = [] - union = Gitlab::SQL::Union. - new([authorized.select(:id), public_and_internal_projects.select(:id)]) + projects << @user.personal_projects.visible_to_user(current_user) if current_user + projects << @user.personal_projects.public_to_user(current_user) - Project.where("projects.id IN (#{union.to_sql})") - end - - def public_projects - @user.personal_projects.public_only - end - - def public_and_internal_projects - @user.personal_projects.public_and_internal_only + projects end end diff --git a/app/finders/projects_finder.rb b/app/finders/projects_finder.rb index 3b4e0362e04..2f0a9659d15 100644 --- a/app/finders/projects_finder.rb +++ b/app/finders/projects_finder.rb @@ -1,76 +1,18 @@ -class ProjectsFinder - # Returns all projects, optionally including group projects a user has access - # to. - # - # ## Examples - # - # Retrieving all public projects: - # - # ProjectsFinder.new.execute - # - # Retrieving all public/internal projects and those the given user has access - # to: - # - # ProjectsFinder.new.execute(some_user) - # - # Retrieving all public/internal projects as well as the group's projects the - # user has access to: - # - # ProjectsFinder.new.execute(some_user, group: some_group) - # - # Returns an ActiveRecord::Relation. +class ProjectsFinder < UnionFinder def execute(current_user = nil, options = {}) - group = options[:group] + segments = all_projects(current_user) - if group - segments = group_projects(current_user, group) - else - segments = all_projects(current_user) - end - - if segments.length > 1 - union = Gitlab::SQL::Union.new(segments.map { |s| s.select(:id) }) - - Project.where("projects.id IN (#{union.to_sql})") - else - segments.first - end + find_union(segments, Project) end private - def group_projects(current_user, group) - if current_user - [ - group_projects_for_user(current_user, group), - group.projects.public_and_internal_only - ] - else - [group.projects.public_only] - end - end - def all_projects(current_user) - if current_user - [current_user.authorized_projects, public_and_internal_projects] - else - [Project.public_only] - end - end - - def group_projects_for_user(current_user, group) - if group.users.include?(current_user) - group.projects - else - group.projects.visible_to_user(current_user) - end - end + projects = [] - def public_projects - Project.unscoped.public_only - end + projects << current_user.authorized_projects if current_user + projects << Project.unscoped.public_to_user(current_user) - def public_and_internal_projects - Project.unscoped.public_and_internal_only + projects end end diff --git a/app/finders/snippets_finder.rb b/app/finders/snippets_finder.rb index 07b5759443b..a41172816b8 100644 --- a/app/finders/snippets_finder.rb +++ b/app/finders/snippets_finder.rb @@ -4,7 +4,7 @@ class SnippetsFinder case filter when :all then - snippets(current_user).fresh.non_expired + snippets(current_user).fresh when :by_user then by_user(current_user, params[:user], params[:scope]) when :by_project @@ -27,7 +27,7 @@ class SnippetsFinder end def by_user(current_user, user, scope) - snippets = user.snippets.fresh.non_expired + snippets = user.snippets.fresh return snippets.are_public unless current_user @@ -48,7 +48,7 @@ class SnippetsFinder end def by_project(current_user, project) - snippets = project.snippets.fresh.non_expired + snippets = project.snippets.fresh if current_user if project.team.member?(current_user.id) diff --git a/app/finders/union_finder.rb b/app/finders/union_finder.rb new file mode 100644 index 00000000000..33cd1a491f3 --- /dev/null +++ b/app/finders/union_finder.rb @@ -0,0 +1,11 @@ +class UnionFinder + def find_union(segments, klass) + if segments.length > 1 + union = Gitlab::SQL::Union.new(segments.map { |s| s.select(:id) }) + + klass.where("#{klass.table_name}.id IN (#{union.to_sql})") + else + segments.first + end + end +end |