From 152697fa8e09b5ac392a1ea31fb7ef627a99786c Mon Sep 17 00:00:00 2001 From: Jon Jensen Date: Sun, 17 May 2015 18:05:43 -0600 Subject: [PATCH] add ability to ignore keys, closes #22 Immigrant.ignore_keys allows you to specify a list of keys that should be ignored (both in the migration generator and the rake task). this is useful if you have associations spanning schemas or databases (see #21) just create an config/initializers/immigrant.rb file with something like the following: Immigrant.ignore_keys = [ { from_table: "users", column: "account_id" }, # etc ] note that you need to specify both the from_table and the column --- lib/immigrant.rb | 25 ++++++++++++++++++++----- test/immigrant_test.rb | 24 ++++++++++++++++++++++++ 2 files changed, 44 insertions(+), 5 deletions(-) diff --git a/lib/immigrant.rb b/lib/immigrant.rb index d77eff3..4bd6585 100644 --- a/lib/immigrant.rb +++ b/lib/immigrant.rb @@ -1,13 +1,28 @@ require 'active_support/all' module Immigrant + class << self + # expected format: + # [{from_table: "the_table", column: "the_column"}, ...]" + attr_writer :ignore_keys + + def ignore_keys + @ignore_keys ||= [] + end + end + class KeyFinder def infer_keys(db_keys = current_foreign_keys, classes = model_classes) - database_keys = db_keys.inject({}) { |hash, foreign_key| - hash[foreign_key.hash_key] = foreign_key - hash - } + database_keys = Hash[db_keys.map { |foreign_key| + [foreign_key.hash_key, foreign_key] + }] + + ignore_keys = Hash[Immigrant.ignore_keys.map { |key| + [[key[:from_table], key[:column]], true] + }] + model_keys, warnings = model_keys(classes) + new_keys = [] model_keys.keys.each do |hash_key| foreign_key = model_keys[hash_key] @@ -18,7 +33,7 @@ def infer_keys(db_keys = current_foreign_keys, classes = model_classes) if current_key.to_table != foreign_key.to_table || current_key.options[:primary_key] != foreign_key.options[:primary_key] warnings[hash_key] = "Skipping #{foreign_key.from_table}.#{foreign_key.options[:column]}: its association references a different key/table than its current foreign key" end - else + elsif !ignore_keys[hash_key] new_keys << foreign_key end end diff --git a/test/immigrant_test.rb b/test/immigrant_test.rb index 7ec50a1..b7fc565 100644 --- a/test/immigrant_test.rb +++ b/test/immigrant_test.rb @@ -455,6 +455,30 @@ class Widget < ActiveRecord::Base end end + test 'ignore_keys should be respected' do + given <<-CODE + class User < ActiveRecord::Base; end + class Category < ActiveRecord::Base; end + class Widget < ActiveRecord::Base + belongs_to :user + belongs_to :category + end + CODE + + Immigrant.ignore_keys = [{:from_table => "widgets", :column => "category_id"}] + begin + assert_equal( + [foreign_key_definition( + 'widgets', 'users', + :column => 'user_id', :primary_key => 'id' + )], + infer_keys + ) + ensure + Immigrant.ignore_keys = [] + end + end + test 'ForeignKeyDefinition#to_ruby should correctly dump the key' do if ActiveRecord::VERSION::STRING < '4.2.' definition = foreign_key_definition('foos', 'bars', dependent: 'delete')