😊
Rakeタスクの実行に前処理を追加する(Multi DB対応)
やりたいこと
Rakeタスクの実行に前処理を追加する をMulti DBにも対応させる。
Multi DB環境では、 db:drop:primary
db:drop:secondary
のようにデータベースを指定して実行することができるので、これらの実行時前に変数のチェックを行う。
前提:Multi DBの設定
primary
secondary
の2つのDBを仮定する。
database.yml
default: &default
adapter: sqlite3
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
timeout: 5000
development:
primary:
<<: *default
database: storage/development_primary.sqlite3
secondary:
<<: *default
database: storage/development_secondary.sqlite3
解1:愚直に列挙する
正直、データベースが増える頻度を考えるとこれで十分ではある。
Rakefile
namespace :db do
task :abort_if_no_run do
abort 'Please set RUN environment variable.' if Rails.env.production? && ENV['RUN'] != 'true'
end
Rake::Task['db:drop'].enhance(['abort_if_no_run'])
Rake::Task['db:drop:primary'].enhance(['abort_if_no_run'])
Rake::Task['db:drop:secondary'].enhance(['abort_if_no_run'])
end
ループにしてもいいが、可読性や記述量の観点で本質としてはそこまで差がない。
Rakefile
namespace :db do
task :abort_if_no_run do
abort 'Please set RUN environment variable.' if Rails.env.production? && ENV['RUN'] != 'true'
end
Rake::Task['db:drop'].enhance(['abort_if_no_run'])
%w[primary secondary].each do |database|
Rake::Task["db:drop:#{database}"].enhance(['abort_if_no_run'])
end
end
解2:configを読んでループで指定する
ActiveRecord::Base.configurations.configs_for(env_name: Rails.env)
でdbのリストが取れるので、それをループして処理する。
ただ、そのまま実行しても空の配列が返ってくるので、 db:load_config
のタスクを実行しておく。
Rakefile
namespace :db do
task :abort_if_no_run do
abort 'Please set RUN environment variable.' if Rails.env.production? && ENV['RUN'] != 'true'
end
Rake::Task['db:load_config'].invoke
ActiveRecord::Base.configurations.configs_for(env_name: Rails.env).each do |db_config|
Rake::Task["db:drop:#{db_config.name}"].enhance(['abort_if_no_run'])
end
Rake::Task['db:drop'].enhance(['abort_if_no_run'])
end
実行結果
./bin/rails db:drop:primary RAILS_ENV=production
Please set RUN environment variable.
Discussion