From 015f45f7032af63c43439bcf509a723d3244eea8 Mon Sep 17 00:00:00 2001 From: "Ben Sheldon [he/him]" Date: Sat, 2 Dec 2023 09:16:58 -0800 Subject: [PATCH] Fix: create new conditional indexes _before_ dropping overlapping indexes (#1165) Fixes issue introduced in #1163 --- ...28075428_recreate_good_job_cron_indexes.rb | 27 ----------- ..._good_job_cron_indexes_with_conditional.rb | 45 +++++++++++++++++++ .../migrations/create_good_jobs.rb.erb | 4 +- .../07_recreate_good_job_cron_indexes.rb.erb | 27 ----------- ...d_job_cron_indexes_with_conditional.rb.erb | 45 +++++++++++++++++++ 5 files changed, 92 insertions(+), 56 deletions(-) delete mode 100644 demo/db/migrate/20231128075428_recreate_good_job_cron_indexes.rb create mode 100644 demo/db/migrate/20231128075428_recreate_good_job_cron_indexes_with_conditional.rb delete mode 100644 lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes.rb.erb create mode 100644 lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes_with_conditional.rb.erb diff --git a/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes.rb b/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes.rb deleted file mode 100644 index 4925dd918..000000000 --- a/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes.rb +++ /dev/null @@ -1,27 +0,0 @@ -# frozen_string_literal: true - -class RecreateGoodJobCronIndexes < ActiveRecord::Migration[7.1] - disable_ddl_transaction! - - def change - reversible do |dir| - dir.up do - if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) - remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at - end - if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) - remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at - end - - unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) - add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", - name: :index_good_jobs_on_cron_key_and_created_at, algorithm: :concurrently - end - unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) - add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, - name: :index_good_jobs_on_cron_key_and_cron_at, algorithm: :concurrently - end - end - end - end -end diff --git a/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes_with_conditional.rb b/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes_with_conditional.rb new file mode 100644 index 000000000..56cab35c3 --- /dev/null +++ b/demo/db/migrate/20231128075428_recreate_good_job_cron_indexes_with_conditional.rb @@ -0,0 +1,45 @@ +# frozen_string_literal: true + +class RecreateGoodJobCronIndexesWithConditional < ActiveRecord::Migration[7.1] + disable_ddl_transaction! + + def change + reversible do |dir| + dir.up do + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at_cond) + add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", + name: :index_good_jobs_on_cron_key_and_created_at_cond, algorithm: :concurrently + end + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at_cond) + add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, + name: :index_good_jobs_on_cron_key_and_cron_at_cond, algorithm: :concurrently + end + + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at + end + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at + end + end + + dir.down do + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) + add_index :good_jobs, [:cron_key, :created_at], + name: :index_good_jobs_on_cron_key_and_created_at, algorithm: :concurrently + end + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) + add_index :good_jobs, [:cron_key, :cron_at], unique: true, + name: :index_good_jobs_on_cron_key_and_cron_at, algorithm: :concurrently + end + + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at_cond) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at_cond + end + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at_cond) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at_cond + end + end + end + end +end diff --git a/lib/generators/good_job/templates/install/migrations/create_good_jobs.rb.erb b/lib/generators/good_job/templates/install/migrations/create_good_jobs.rb.erb index 1465c9a34..7973d2b13 100644 --- a/lib/generators/good_job/templates/install/migrations/create_good_jobs.rb.erb +++ b/lib/generators/good_job/templates/install/migrations/create_good_jobs.rb.erb @@ -74,8 +74,8 @@ class CreateGoodJobs < ActiveRecord::Migration<%= migration_version %> add_index :good_jobs, [:queue_name, :scheduled_at], where: "(finished_at IS NULL)", name: :index_good_jobs_on_queue_name_and_scheduled_at add_index :good_jobs, [:active_job_id, :created_at], name: :index_good_jobs_on_active_job_id_and_created_at add_index :good_jobs, :concurrency_key, where: "(finished_at IS NULL)", name: :index_good_jobs_on_concurrency_key_when_unfinished - add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", name: :index_good_jobs_on_cron_key_and_created_at - add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, name: :index_good_jobs_on_cron_key_and_cron_at + add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", name: :index_good_jobs_on_cron_key_and_created_at_cond + add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, name: :index_good_jobs_on_cron_key_and_cron_at_cond add_index :good_jobs, [:active_job_id], name: :index_good_jobs_on_active_job_id add_index :good_jobs, [:finished_at], where: "retried_good_job_id IS NULL AND finished_at IS NOT NULL", name: :index_good_jobs_jobs_on_finished_at add_index :good_jobs, [:priority, :created_at], order: { priority: "DESC NULLS LAST", created_at: :asc }, diff --git a/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes.rb.erb b/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes.rb.erb deleted file mode 100644 index 10ccfaab1..000000000 --- a/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes.rb.erb +++ /dev/null @@ -1,27 +0,0 @@ -# frozen_string_literal: true - -class RecreateGoodJobCronIndexes < ActiveRecord::Migration<%= migration_version %> - disable_ddl_transaction! - - def change - reversible do |dir| - dir.up do - if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) - remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at - end - if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) - remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at - end - - unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) - add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", - name: :index_good_jobs_on_cron_key_and_created_at, algorithm: :concurrently - end - unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) - add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, - name: :index_good_jobs_on_cron_key_and_cron_at, algorithm: :concurrently - end - end - end - end -end diff --git a/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes_with_conditional.rb.erb b/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes_with_conditional.rb.erb new file mode 100644 index 000000000..5b3c54001 --- /dev/null +++ b/lib/generators/good_job/templates/update/migrations/07_recreate_good_job_cron_indexes_with_conditional.rb.erb @@ -0,0 +1,45 @@ +# frozen_string_literal: true + +class RecreateGoodJobCronIndexesWithConditional < ActiveRecord::Migration<%= migration_version %> + disable_ddl_transaction! + + def change + reversible do |dir| + dir.up do + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at_cond) + add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", + name: :index_good_jobs_on_cron_key_and_created_at_cond, algorithm: :concurrently + end + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at_cond) + add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, + name: :index_good_jobs_on_cron_key_and_cron_at_cond, algorithm: :concurrently + end + + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at + end + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at + end + end + + dir.down do + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at) + add_index :good_jobs, [:cron_key, :created_at], where: "(cron_key IS NOT NULL)", + name: :index_good_jobs_on_cron_key_and_created_at, algorithm: :concurrently + end + unless connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at) + add_index :good_jobs, [:cron_key, :cron_at], where: "(cron_key IS NOT NULL)", unique: true, + name: :index_good_jobs_on_cron_key_and_cron_at, algorithm: :concurrently + end + + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_created_at_cond) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_created_at_cond + end + if connection.index_name_exists?(:good_jobs, :index_good_jobs_on_cron_key_and_cron_at_cond) + remove_index :good_jobs, name: :index_good_jobs_on_cron_key_and_cron_at_cond + end + end + end + end +end