Add rake task `db:obsolete_ignored_columns`
Show a list of obsolete `ignored_columns`
This commit is contained in:
parent
0abc902576
commit
50c647af51
|
@ -216,3 +216,13 @@ bundle exec rake routes
|
||||||
|
|
||||||
Since these take some time to create, it's often helpful to save the output to
|
Since these take some time to create, it's often helpful to save the output to
|
||||||
a file for quick reference.
|
a file for quick reference.
|
||||||
|
|
||||||
|
## Show obsolete `ignored_columns`
|
||||||
|
|
||||||
|
To see a list of all obsolete `ignored_columns` run:
|
||||||
|
|
||||||
|
```
|
||||||
|
bundle exec rake db:obsolete_ignored_columns
|
||||||
|
```
|
||||||
|
|
||||||
|
Feel free to remove their definitions from their `ignored_columns` definitions.
|
||||||
|
|
|
@ -0,0 +1,38 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
module Gitlab
|
||||||
|
module Database
|
||||||
|
# Checks which `ignored_columns` can be safely removed by scanning
|
||||||
|
# the current schema for all `ApplicationRecord` descendants.
|
||||||
|
class ObsoleteIgnoredColumns
|
||||||
|
def initialize(base = ApplicationRecord)
|
||||||
|
@base = base
|
||||||
|
end
|
||||||
|
|
||||||
|
def execute
|
||||||
|
@base.descendants.map do |klass|
|
||||||
|
next if klass.abstract_class?
|
||||||
|
|
||||||
|
safe_to_remove = ignored_columns_safe_to_remove_for(klass)
|
||||||
|
next if safe_to_remove.empty?
|
||||||
|
|
||||||
|
[klass.name, safe_to_remove]
|
||||||
|
end.compact.sort_by(&:first)
|
||||||
|
end
|
||||||
|
|
||||||
|
private
|
||||||
|
|
||||||
|
def ignored_columns_safe_to_remove_for(klass)
|
||||||
|
ignored = klass.ignored_columns.map(&:to_s)
|
||||||
|
|
||||||
|
return [] if ignored.empty?
|
||||||
|
|
||||||
|
schema = klass.connection.schema_cache.columns_hash(klass.table_name)
|
||||||
|
existing = schema.values.map(&:name)
|
||||||
|
|
||||||
|
used = ignored & existing
|
||||||
|
ignored - used
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
|
@ -0,0 +1,21 @@
|
||||||
|
desc 'Show a list of obsolete `ignored_columns`'
|
||||||
|
task 'db:obsolete_ignored_columns' => :environment do
|
||||||
|
list = Gitlab::Database::ObsoleteIgnoredColumns.new.execute
|
||||||
|
|
||||||
|
if list.empty?
|
||||||
|
puts 'No obsolete `ignored_columns` found.'
|
||||||
|
else
|
||||||
|
puts 'The following `ignored_columns` are obsolete and can be removed:'
|
||||||
|
|
||||||
|
list.each do |name, ignored_columns|
|
||||||
|
puts "- #{name}: #{ignored_columns.join(', ')}"
|
||||||
|
end
|
||||||
|
|
||||||
|
puts <<~TEXT
|
||||||
|
|
||||||
|
WARNING: Removing columns is tricky because running GitLab processes may still be using the columns.
|
||||||
|
|
||||||
|
See also https://docs.gitlab.com/ee/development/what_requires_downtime.html#dropping-columns
|
||||||
|
TEXT
|
||||||
|
end
|
||||||
|
end
|
|
@ -0,0 +1,43 @@
|
||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
require 'spec_helper'
|
||||||
|
|
||||||
|
describe Gitlab::Database::ObsoleteIgnoredColumns do
|
||||||
|
module Testing
|
||||||
|
class MyBase < ApplicationRecord
|
||||||
|
end
|
||||||
|
|
||||||
|
class SomeAbstract < MyBase
|
||||||
|
self.abstract_class = true
|
||||||
|
|
||||||
|
self.table_name = 'projects'
|
||||||
|
|
||||||
|
self.ignored_columns += %i[unused]
|
||||||
|
end
|
||||||
|
|
||||||
|
class B < MyBase
|
||||||
|
self.table_name = 'issues'
|
||||||
|
|
||||||
|
self.ignored_columns += %i[id other]
|
||||||
|
end
|
||||||
|
|
||||||
|
class A < SomeAbstract
|
||||||
|
self.ignored_columns += %i[id also_unused]
|
||||||
|
end
|
||||||
|
|
||||||
|
class C < MyBase
|
||||||
|
self.table_name = 'users'
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
subject { described_class.new(Testing::MyBase) }
|
||||||
|
|
||||||
|
describe '#execute' do
|
||||||
|
it 'returns a list of class names and columns pairs' do
|
||||||
|
expect(subject.execute).to eq([
|
||||||
|
['Testing::A', %w(unused also_unused)],
|
||||||
|
['Testing::B', %w(other)]
|
||||||
|
])
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
Loading…
Reference in New Issue