summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorRobert Speicher <robert@gitlab.com>2018-05-30 14:41:46 +0000
committerRobert Speicher <robert@gitlab.com>2018-05-30 14:41:46 +0000
commita8c97187f07cc4feeec9347967a12680cf5aec37 (patch)
tree58a72458ca83ee05f32b92b8db24f3b76880057f /lib
parent2c977029feb756955235f16a06e46d20adb1f557 (diff)
parentcda2c5e76f18ff773ed0cac548bbf5d62a9adb26 (diff)
downloadgitlab-ce-a8c97187f07cc4feeec9347967a12680cf5aec37.tar.gz
Merge branch 'dm-api-projects-members-preload' into 'master'
Only preload member records for the relevant projects/groups/user in projects API See merge request gitlab-org/gitlab-ce!18945
Diffstat (limited to 'lib')
-rw-r--r--lib/api/entities.rb29
-rw-r--r--lib/api/projects.rb7
2 files changed, 20 insertions, 16 deletions
diff --git a/lib/api/entities.rb b/lib/api/entities.rb
index 49cd4fccc63..c4537036a3a 100644
--- a/lib/api/entities.rb
+++ b/lib/api/entities.rb
@@ -832,8 +832,8 @@ module API
class ProjectWithAccess < Project
expose :permissions do
expose :project_access, using: Entities::ProjectAccess do |project, options|
- if options.key?(:project_members)
- (options[:project_members] || []).find { |member| member.source_id == project.id }
+ if options[:project_members]
+ options[:project_members].find { |member| member.source_id == project.id }
else
project.project_member(options[:current_user])
end
@@ -841,8 +841,8 @@ module API
expose :group_access, using: Entities::GroupAccess do |project, options|
if project.group
- if options.key?(:group_members)
- (options[:group_members] || []).find { |member| member.source_id == project.namespace_id }
+ if options[:group_members]
+ options[:group_members].find { |member| member.source_id == project.namespace_id }
else
project.group.group_member(options[:current_user])
end
@@ -853,13 +853,24 @@ module API
def self.preload_relation(projects_relation, options = {})
relation = super(projects_relation, options)
- unless options.key?(:group_members)
- relation = relation.preload(group: [group_members: [:source, user: [notification_settings: :source]]])
+ # MySQL doesn't support LIMIT inside an IN subquery
+ if Gitlab::Database.mysql?
+ project_ids = relation.pluck('projects.id')
+ namespace_ids = relation.pluck(:namespace_id)
+ else
+ project_ids = relation.select('projects.id')
+ namespace_ids = relation.select(:namespace_id)
end
- unless options.key?(:project_members)
- relation = relation.preload(project_members: [:source, user: [notification_settings: :source]])
- end
+ options[:project_members] = options[:current_user]
+ .project_members
+ .where(source_id: project_ids)
+ .preload(:source, user: [notification_settings: :source])
+
+ options[:group_members] = options[:current_user]
+ .group_members
+ .where(source_id: namespace_ids)
+ .preload(:source, user: [notification_settings: :source])
relation
end
diff --git a/lib/api/projects.rb b/lib/api/projects.rb
index 8871792060b..3ef3680c5d9 100644
--- a/lib/api/projects.rb
+++ b/lib/api/projects.rb
@@ -58,16 +58,9 @@ module API
projects = paginate(projects)
projects, options = with_custom_attributes(projects, options)
- if current_user
- project_members = current_user.project_members.preload(:source, user: [notification_settings: :source])
- group_members = current_user.group_members.preload(:source, user: [notification_settings: :source])
- end
-
options = options.reverse_merge(
with: current_user ? Entities::ProjectWithAccess : Entities::BasicProjectDetails,
statistics: params[:statistics],
- project_members: project_members,
- group_members: group_members,
current_user: current_user
)
options[:with] = Entities::BasicProjectDetails if params[:simple]