diff --git a/CHANGELOG b/CHANGELOG
index 658bd92a8248e49bdb73e3378cab02f39dc370e7..c6c2220b133bb424aeccec0905eee103fcd5ac4c 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -110,6 +110,7 @@ v 8.11.0 (unreleased)
   - Each `File::exists?` replaced to `File::exist?` because of deprecate since ruby version 2.2.0
   - Add auto-completition in pipeline (Katarzyna Kobierska Ula Budziszewska)
   - Fix a memory leak caused by Banzai::Filter::SanitizationFilter
+  - Speed up todos queries by limiting the projects set we join with
 
 v 8.10.5
   - Add a data migration to fix some missing timestamps in the members table. !5670
diff --git a/app/finders/projects_finder.rb b/app/finders/projects_finder.rb
index 2f0a9659d15b878a47c8555c6a0daca56d43bae2..56877b6d75ad2e19ccd0212f8abb9d492e863010 100644
--- a/app/finders/projects_finder.rb
+++ b/app/finders/projects_finder.rb
@@ -1,6 +1,7 @@
 class ProjectsFinder < UnionFinder
-  def execute(current_user = nil, options = {})
+  def execute(current_user = nil, options = {}, &block)
     segments = all_projects(current_user)
+    segments.map!(&block) if block
 
     find_union(segments, Project)
   end
diff --git a/app/finders/todos_finder.rb b/app/finders/todos_finder.rb
index ff866c2faa502e219f8bb06603dfa72ddb997c60..9b24a86e1c19d7af665dab7b1ecf78e02bcd8275 100644
--- a/app/finders/todos_finder.rb
+++ b/app/finders/todos_finder.rb
@@ -27,9 +27,11 @@ def execute
     items = by_action_id(items)
     items = by_action(items)
     items = by_author(items)
-    items = by_project(items)
     items = by_state(items)
     items = by_type(items)
+    # Filtering by project HAS TO be the last because we use
+    # the project IDs yielded by the todos query thus far
+    items = by_project(items)
 
     items.reorder(id: :desc)
   end
@@ -91,13 +93,10 @@ def project
     @project
   end
 
-  def projects
-    return @projects if defined?(@projects)
-
-    if project?
-      @projects = project
-    else
-      @projects = ProjectsFinder.new.execute(current_user)
+  def projects(items)
+    item_project_ids = items.reorder(nil).select(:project_id)
+    ProjectsFinder.new.execute(current_user) do |relation|
+      relation.where(id: item_project_ids)
     end
   end
 
@@ -136,8 +135,9 @@ def by_author(items)
   def by_project(items)
     if project?
       items = items.where(project: project)
-    elsif projects
-      items = items.merge(projects).joins(:project)
+    else
+      item_projects = projects(items)
+      items = items.merge(item_projects).joins(:project)
     end
 
     items