From 3aa6b25fb5ab4957b9d668927e70dc9690e084db Mon Sep 17 00:00:00 2001 From: Samuel Young Date: Tue, 16 Sep 2025 14:22:08 +0100 Subject: [PATCH] CLDC-4028: Export records where a related one has updated for instance, re-export all users in an org if the name updates rework the export code a little to allow for this to be expressed cleanly --- .../exports/lettings_log_export_service.rb | 34 ++++++++++++++----- .../exports/organisation_export_service.rb | 29 +++++++--------- .../exports/sales_log_export_service.rb | 34 ++++++++++++++----- app/services/exports/user_export_service.rb | 21 +++++++----- app/services/exports/xml_export_service.rb | 10 ++++++ 5 files changed, 87 insertions(+), 41 deletions(-) diff --git a/app/services/exports/lettings_log_export_service.rb b/app/services/exports/lettings_log_export_service.rb index 1ad44cbe4..4e1fe2019 100644 --- a/app/services/exports/lettings_log_export_service.rb +++ b/app/services/exports/lettings_log_export_service.rb @@ -30,14 +30,32 @@ module Exports "core_#{year}_#{year + 1}_apr_mar_#{base_number_str}_#{increment_str}".downcase end - def retrieve_resources(recent_export, full_update, year) - if !full_update && recent_export - params = { from: recent_export.started_at, to: @start_time } - LettingsLog.exportable.where("(updated_at >= :from AND updated_at <= :to) OR (values_updated_at IS NOT NULL AND values_updated_at >= :from AND values_updated_at <= :to)", params).filter_by_year(year) - else - params = { to: @start_time } - LettingsLog.exportable.where("updated_at <= :to", params).filter_by_year(year) - end + def retrieve_resources_from_range(range, year) + relation = LettingsLog.exportable.filter_by_year(year).left_joins(:created_by, :updated_by, :assigned_to, :owning_organisation, :managing_organisation) + + ids = relation + .where({ updated_at: range }) + .or( + relation.where.not(values_updated_at: nil).where(values_updated_at: range), + ) + .or( + relation.where.not({ created_by: { updated_at: nil } }).where({ created_by: { updated_at: range } }), + ) + .or( + relation.where.not({ updated_by: { updated_at: nil } }).where({ updated_by: { updated_at: range } }), + ) + .or( + relation.where.not({ assigned_to: { updated_at: nil } }).where({ assigned_to: { updated_at: range } }), + ) + .or( + relation.where.not({ owning_organisation: { updated_at: nil } }).where({ owning_organisation: { updated_at: range } }), + ) + .or( + relation.where.not({ managing_organisation: { updated_at: nil } }).where({ managing_organisation: { updated_at: range } }), + ) + .pluck(:id) + + LettingsLog.where(id: ids) end def apply_cds_transformation(lettings_log, export_mode) diff --git a/app/services/exports/organisation_export_service.rb b/app/services/exports/organisation_export_service.rb index 0e8967bbc..4cb98bc2c 100644 --- a/app/services/exports/organisation_export_service.rb +++ b/app/services/exports/organisation_export_service.rb @@ -25,24 +25,19 @@ module Exports "organisations_2024_2025_apr_mar_#{base_number_str}_#{increment_str}".downcase end - def retrieve_resources(recent_export, full_update, _year) - if !full_update && recent_export - params = { from: recent_export.started_at, to: @start_time } + def retrieve_resources_from_range(range, _year) + relation = Organisation.left_joins(:users, :organisation_name_changes) + ids = relation + .where({ updated_at: range }) + .or( + relation.where(organisation_name_changes: { created_at: range }), + ) + .or( + relation.where(users: { is_dpo: true, updated_at: range }), + ) + .pluck(:id) - Organisation - .where(updated_at: params[:from]..params[:to]) - .or( - Organisation.where(id: OrganisationNameChange.where(created_at: params[:from]..params[:to]).select(:organisation_id)), - ) - else - params = { to: @start_time } - - Organisation - .where("updated_at <= :to", params) - .or( - Organisation.where(id: OrganisationNameChange.where("created_at <= :to", params).select(:organisation_id)), - ) - end + Organisation.where(id: ids) end def build_export_xml(organisations) diff --git a/app/services/exports/sales_log_export_service.rb b/app/services/exports/sales_log_export_service.rb index 9cac14207..db525dde4 100644 --- a/app/services/exports/sales_log_export_service.rb +++ b/app/services/exports/sales_log_export_service.rb @@ -30,14 +30,32 @@ module Exports "core_sales_#{year}_#{year + 1}_apr_mar_#{base_number_str}_#{increment_str}".downcase end - def retrieve_resources(recent_export, full_update, year) - if !full_update && recent_export - params = { from: recent_export.started_at, to: @start_time } - SalesLog.exportable.where("(updated_at >= :from AND updated_at <= :to) OR (values_updated_at IS NOT NULL AND values_updated_at >= :from AND values_updated_at <= :to)", params).filter_by_year(year) - else - params = { to: @start_time } - SalesLog.exportable.where("updated_at <= :to", params).filter_by_year(year) - end + def retrieve_resources_from_range(range, year) + relation = SalesLog.exportable.filter_by_year(year).left_joins(:created_by, :updated_by, :assigned_to, :owning_organisation, :managing_organisation) + + ids = relation + .where({ updated_at: range }) + .or( + relation.where.not(values_updated_at: nil).where(values_updated_at: range), + ) + .or( + relation.where.not({ created_by: { updated_at: nil } }).where({ created_by: { updated_at: range } }), + ) + .or( + relation.where.not({ updated_by: { updated_at: nil } }).where({ updated_by: { updated_at: range } }), + ) + .or( + relation.where.not({ assigned_to: { updated_at: nil } }).where({ assigned_to: { updated_at: range } }), + ) + .or( + relation.where.not({ owning_organisation: { updated_at: nil } }).where({ owning_organisation: { updated_at: range } }), + ) + .or( + relation.where.not({ managing_organisation: { updated_at: nil } }).where({ managing_organisation: { updated_at: range } }), + ) + .pluck(:id) + + SalesLog.where(id: ids) end def apply_cds_transformation(sales_log, _export_mode) diff --git a/app/services/exports/user_export_service.rb b/app/services/exports/user_export_service.rb index 177daee1d..d79a4df49 100644 --- a/app/services/exports/user_export_service.rb +++ b/app/services/exports/user_export_service.rb @@ -25,14 +25,19 @@ module Exports "users_2024_2025_apr_mar_#{base_number_str}_#{increment_str}".downcase end - def retrieve_resources(recent_export, full_update, _year) - if !full_update && recent_export - params = { from: recent_export.started_at, to: @start_time } - User.where("(updated_at >= :from AND updated_at <= :to) OR (values_updated_at IS NOT NULL AND values_updated_at >= :from AND values_updated_at <= :to)", params) - else - params = { to: @start_time } - User.where("updated_at <= :to", params) - end + def retrieve_resources_from_range(range, _year) + relation = User.left_joins(organisation: :organisation_name_changes) + ids = relation + .where({ updated_at: range }) + .or( + relation.where.not(organisations: { updated_at: nil }).where(organisations: { updated_at: range }), + ) + .or( + relation.where(organisation_name_changes: { created_at: range }), + ) + .pluck(:id) + + User.where(id: ids) end def build_export_xml(users) diff --git a/app/services/exports/xml_export_service.rb b/app/services/exports/xml_export_service.rb index d499dd518..703d94f7d 100644 --- a/app/services/exports/xml_export_service.rb +++ b/app/services/exports/xml_export_service.rb @@ -31,6 +31,16 @@ module Exports Export.new(collection:, year:, started_at: @start_time, base_number:, increment_number:) end + def retrieve_resources(recent_export, full_update, year) + range = if !full_update && recent_export + recent_export.started_at..@start_time + else + ..@start_time + end + + retrieve_resources_from_range(range, year) + end + def write_export_archive(export, year, recent_export, full_update) archive = get_archive_name(year, export.base_number, export.increment_number)