Commit 40ecff12 authored by Gabriel Mazetto's avatar Gabriel Mazetto

Improve FDW performance with a workaround

parent 181e84e3
......@@ -11,7 +11,11 @@ class Admin::GeoProjectsController < Admin::ApplicationController
case params[:sync_status]
when 'never'
@projects = finder.never_synced_projects.page(params[:page])
# This method uses FDW heavily and due to optimizations we need to inject the pagination
# earlier as well, so we need the block to do that
@projects = finder.never_synced_projects do |fdw_relation|
fdw_relation.page(params[:page])
end.page(params[:page])
when 'failed'
@registries = finder.failed_projects.page(params[:page])
when 'pending'
......
......@@ -63,16 +63,23 @@ module Geo
# We include here both projects without a corresponding ProjectRegistry
# or projects that have never successfully synced.
#
# @yield [ActiveRecord::Relation]
# @return [Geo::Fdw::Project] Projects that has never been fully synced
def never_synced_projects
no_project_registry = project_registry[:project_id].eq(nil)
no_repository_synced = project_registry[:last_repository_successful_sync_at].eq(nil)
Geo::Fdw::Project.joins("LEFT OUTER JOIN project_registry ON (project_registry.project_id = #{Geo::Fdw::Project.table_name}.id)")
project_ids = Geo::Fdw::Project.select(:id).joins("LEFT OUTER JOIN project_registry ON (project_registry.project_id = #{Geo::Fdw::Project.table_name}.id)")
.where(
no_project_registry
.or(no_repository_synced)
).includes(:project_registry)
.or(no_repository_synced))
# This allows us to inject pagination
if block_given?
project_ids = yield(project_ids)
end
Project.where(id: project_ids.to_a).includes(:project_registry)
end
private
......
......@@ -62,16 +62,12 @@ describe Geo::ProjectRegistryStatusFinder, :geo do
describe '#never_synced_projects' do
it 'returns only FDW projects without registry or with never synced registries' do
fdw_project_with_never_synced_registry_with_failure = Geo::Fdw::Project.find(never_synced_registry_with_failure.project.id)
fdw_project_with_never_synced_registry = Geo::Fdw::Project.find(project_with_never_synced_registry.id)
fdw_project_without_registry = Geo::Fdw::Project.find(project_without_registry.id)
result = subject.never_synced_projects
expect(result).to contain_exactly(
fdw_project_without_registry,
fdw_project_with_never_synced_registry,
fdw_project_with_never_synced_registry_with_failure
project_without_registry,
project_with_never_synced_registry,
never_synced_registry_with_failure.project
)
end
end
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment