immigrant 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/lib/generators/immigration_generator.rb +1 -1
- data/lib/immigrant/compat/3.0.rb +6 -5
- data/lib/immigrant/compat/3.1.rb +6 -5
- data/lib/immigrant/compat/4.0.rb +14 -15
- data/lib/immigrant/compat/4.2.rb +12 -54
- data/lib/immigrant/compat/5.0.rb +1 -0
- data/lib/immigrant/compat/active_record.rb +44 -0
- data/lib/immigrant/compat/foreigner.rb +44 -0
- data/lib/immigrant/compat.rb +8 -52
- data/lib/immigrant/foreign_key_extensions.rb +23 -0
- data/lib/immigrant.rb +90 -32
- data/test/helper.rb +1 -0
- data/test/immigrant_test.rb +150 -128
- metadata +16 -18
- data/lib/immigrant/compat/foreigner_extensions.rb +0 -5
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 083bc4d18b381bf62146a71c000495a4b108fed2
|
4
|
+
data.tar.gz: b096073f024d41aa6362c2d3db3a3014aa8016ba
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: e1fe3e50d541c96400fbb476bcac1ac9176aa51e19b8d7e373398307aa34c0cabbea3a9353f932dd47d39439558fb367418b82eae651cac1fe7368c0d7d35e79
|
7
|
+
data.tar.gz: ce45456a29ebf673ea5a6b987990c70c784387db86804555edebe16812322d31534ff877aae37c071419dae0b26ba6052db2a51b31b5ebd1652f4282b8cbb7a8
|
@@ -3,7 +3,7 @@ require 'rails/generators/active_record'
|
|
3
3
|
class ImmigrationGenerator < ActiveRecord::Generators::Base
|
4
4
|
def create_immigration_file
|
5
5
|
Rails.application.eager_load!
|
6
|
-
@keys, warnings = Immigrant.infer_keys
|
6
|
+
@keys, warnings = Immigrant::KeyFinder.new.infer_keys
|
7
7
|
warnings.values.each{ |warning| $stderr.puts "WARNING: #{warning}" }
|
8
8
|
@keys.each do |key|
|
9
9
|
next unless key.options[:dependent] == :delete
|
data/lib/immigrant/compat/3.0.rb
CHANGED
@@ -1,11 +1,12 @@
|
|
1
|
-
|
2
|
-
ForeignKeyDefinition = ::Foreigner::ConnectionAdapters::ForeignKeyDefinition
|
1
|
+
require_relative 'foreigner'
|
3
2
|
|
3
|
+
module Immigrant
|
4
4
|
TEMPLATE = 'immigration-pre-3.1.rb.erb'
|
5
5
|
FOREIGN_KEY = :primary_key_name
|
6
|
-
ON_DELETE = :dependent
|
7
6
|
|
8
|
-
|
9
|
-
reflection
|
7
|
+
class KeyFinder
|
8
|
+
def qualified_reflection?(reflection, klass)
|
9
|
+
reflection.options[:conditions].present?
|
10
|
+
end
|
10
11
|
end
|
11
12
|
end
|
data/lib/immigrant/compat/3.1.rb
CHANGED
@@ -1,12 +1,13 @@
|
|
1
|
-
|
2
|
-
ForeignKeyDefinition = ::Foreigner::ConnectionAdapters::ForeignKeyDefinition
|
1
|
+
require_relative 'foreigner'
|
3
2
|
|
3
|
+
module Immigrant
|
4
4
|
TEMPLATE = 'immigration.rb.erb'
|
5
5
|
FOREIGN_KEY = :foreign_key
|
6
|
-
ON_DELETE = :dependent
|
7
6
|
|
8
|
-
|
9
|
-
reflection
|
7
|
+
class KeyFinder
|
8
|
+
def qualified_reflection?(reflection, klass)
|
9
|
+
reflection.options[:conditions].present?
|
10
|
+
end
|
10
11
|
end
|
11
12
|
end
|
12
13
|
|
data/lib/immigrant/compat/4.0.rb
CHANGED
@@ -1,22 +1,21 @@
|
|
1
|
-
|
2
|
-
ForeignKeyDefinition = ::Foreigner::ConnectionAdapters::ForeignKeyDefinition
|
1
|
+
require_relative 'foreigner'
|
3
2
|
|
3
|
+
module Immigrant
|
4
4
|
TEMPLATE = 'immigration.rb.erb'
|
5
5
|
FOREIGN_KEY = :foreign_key
|
6
|
-
ON_DELETE = :dependent
|
7
6
|
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
7
|
+
class KeyFinder
|
8
|
+
def qualified_reflection?(reflection, klass)
|
9
|
+
scope = reflection.scope
|
10
|
+
if scope.nil?
|
11
|
+
false
|
12
|
+
else
|
13
|
+
klass.instance_exec(*([nil]*scope.arity), &scope).where_values.present?
|
14
|
+
end
|
15
|
+
rescue
|
16
|
+
# if there's an error evaluating the scope block or whatever, just
|
17
|
+
# err on the side of caution and assume there are conditions
|
18
|
+
true
|
16
19
|
end
|
17
|
-
rescue
|
18
|
-
# if there's an error evaluating the scope block or whatever, just
|
19
|
-
# err on the side of caution and assume there are conditions
|
20
|
-
true
|
21
20
|
end
|
22
21
|
end
|
data/lib/immigrant/compat/4.2.rb
CHANGED
@@ -1,60 +1,18 @@
|
|
1
|
-
|
1
|
+
require_relative 'active_record'
|
2
2
|
|
3
3
|
module Immigrant
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
scope = reflection.scope
|
12
|
-
if scope.nil?
|
13
|
-
false
|
14
|
-
elsif scope.respond_to?(:options)
|
15
|
-
scope.options[:where].present?
|
16
|
-
else
|
17
|
-
klass.instance_exec(*([nil]*scope.arity), &scope).where_values.present?
|
18
|
-
end
|
19
|
-
rescue
|
20
|
-
# if there's an error evaluating the scope block or whatever, just
|
21
|
-
# err on the side of caution and assume there are conditions
|
22
|
-
true
|
23
|
-
end
|
24
|
-
|
25
|
-
module ForeignKeyExtensions
|
26
|
-
# DRY alert: copied from ActiveRecord::SchemaDumper#foreign_keys
|
27
|
-
def dump_foreign_key(foreign_key)
|
28
|
-
parts = [
|
29
|
-
"add_foreign_key #{remove_prefix_and_suffix(foreign_key.from_table).inspect}",
|
30
|
-
remove_prefix_and_suffix(foreign_key.to_table).inspect,
|
31
|
-
]
|
32
|
-
|
33
|
-
if foreign_key.column != foreign_key_column_for(foreign_key.to_table)
|
34
|
-
parts << "column: #{foreign_key.column.inspect}"
|
35
|
-
end
|
36
|
-
|
37
|
-
if foreign_key.custom_primary_key?
|
38
|
-
parts << "primary_key: #{foreign_key.primary_key.inspect}"
|
4
|
+
class KeyFinder
|
5
|
+
def qualified_reflection?(reflection, klass)
|
6
|
+
scope = reflection.scope
|
7
|
+
if scope.nil?
|
8
|
+
false
|
9
|
+
else
|
10
|
+
klass.instance_exec(*([nil]*scope.arity), &scope).where_values.present?
|
39
11
|
end
|
40
|
-
|
41
|
-
if
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
parts << "on_update: #{foreign_key.on_update.inspect}" if foreign_key.on_update
|
46
|
-
parts << "on_delete: #{foreign_key.on_delete.inspect}" if foreign_key.on_delete
|
47
|
-
|
48
|
-
" #{parts.join(', ')}"
|
49
|
-
end
|
50
|
-
|
51
|
-
|
52
|
-
def remove_prefix_and_suffix(table)
|
53
|
-
table.gsub(/^(#{ActiveRecord::Base.table_name_prefix})(.+)(#{ActiveRecord::Base.table_name_suffix})$/, "\\2")
|
54
|
-
end
|
55
|
-
|
56
|
-
def foreign_key_column_for(table_name)
|
57
|
-
"#{table_name.to_s.singularize}_id"
|
12
|
+
rescue
|
13
|
+
# if there's an error evaluating the scope block or whatever, just
|
14
|
+
# err on the side of caution and assume there are conditions
|
15
|
+
true
|
58
16
|
end
|
59
17
|
end
|
60
18
|
end
|
@@ -0,0 +1 @@
|
|
1
|
+
require_relative 'active_record'
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require "active_record/connection_adapters/abstract/schema_definitions"
|
2
|
+
|
3
|
+
module Immigrant
|
4
|
+
ForeignKeyDefinition = ::ActiveRecord::ConnectionAdapters::ForeignKeyDefinition
|
5
|
+
|
6
|
+
TEMPLATE = 'immigration.rb.erb'
|
7
|
+
FOREIGN_KEY = :foreign_key
|
8
|
+
|
9
|
+
module ForeignKeyExtensions
|
10
|
+
# DRY alert: copied from ActiveRecord::SchemaDumper#foreign_keys
|
11
|
+
def dump_foreign_key(foreign_key)
|
12
|
+
parts = [
|
13
|
+
"add_foreign_key #{remove_prefix_and_suffix(foreign_key.from_table).inspect}",
|
14
|
+
remove_prefix_and_suffix(foreign_key.to_table).inspect,
|
15
|
+
]
|
16
|
+
|
17
|
+
if foreign_key.column != foreign_key_column_for(foreign_key.to_table)
|
18
|
+
parts << "column: #{foreign_key.column.inspect}"
|
19
|
+
end
|
20
|
+
|
21
|
+
if foreign_key.custom_primary_key?
|
22
|
+
parts << "primary_key: #{foreign_key.primary_key.inspect}"
|
23
|
+
end
|
24
|
+
|
25
|
+
if foreign_key.name !~ /^fk_rails_[0-9a-f]{10}$/
|
26
|
+
parts << "name: #{foreign_key.name.inspect}"
|
27
|
+
end
|
28
|
+
|
29
|
+
parts << "on_update: #{foreign_key.on_update.inspect}" if foreign_key.on_update
|
30
|
+
parts << "on_delete: #{foreign_key.on_delete.inspect}" if foreign_key.on_delete
|
31
|
+
|
32
|
+
parts.join(', ')
|
33
|
+
end
|
34
|
+
|
35
|
+
|
36
|
+
def remove_prefix_and_suffix(table)
|
37
|
+
table.gsub(/^(#{ActiveRecord::Base.table_name_prefix})(.+)(#{ActiveRecord::Base.table_name_suffix})$/, "\\2")
|
38
|
+
end
|
39
|
+
|
40
|
+
def foreign_key_column_for(table_name)
|
41
|
+
"#{table_name.to_s.singularize}_id"
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
begin
|
2
|
+
require 'foreigner'
|
3
|
+
rescue LoadError
|
4
|
+
$stderr.puts <<-ERR.strip_heredoc
|
5
|
+
|
6
|
+
ERROR: immigrant requires the foreigner gem (unless you are on rails 4.2+)
|
7
|
+
|
8
|
+
To fix this, add the following to your Gemfile:
|
9
|
+
|
10
|
+
gem "foreigner", "~> 1.2"
|
11
|
+
|
12
|
+
Or just upgrade rails ;) ... lol, "just"
|
13
|
+
|
14
|
+
ERR
|
15
|
+
exit 1
|
16
|
+
end
|
17
|
+
Foreigner.load
|
18
|
+
|
19
|
+
module Immigrant
|
20
|
+
ForeignKeyDefinition = ::Foreigner::ConnectionAdapters::ForeignKeyDefinition
|
21
|
+
|
22
|
+
module ForeignKeyExtensions
|
23
|
+
include Foreigner::SchemaDumper::ClassMethods
|
24
|
+
|
25
|
+
def self.included(klass)
|
26
|
+
# ForeignKeyExtensions already overrides initialize; override it
|
27
|
+
# some more
|
28
|
+
klass.send(:include, Module.new{
|
29
|
+
def initialize(from_table, to_table, options)
|
30
|
+
options.delete(:on_update)
|
31
|
+
options[:dependent] = normalize_dependent(options.delete(:on_delete))
|
32
|
+
super
|
33
|
+
end
|
34
|
+
})
|
35
|
+
end
|
36
|
+
|
37
|
+
def normalize_dependent(value)
|
38
|
+
case value
|
39
|
+
when :cascade then :delete
|
40
|
+
else value
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
data/lib/immigrant/compat.rb
CHANGED
@@ -1,57 +1,13 @@
|
|
1
1
|
version = ActiveRecord::VERSION::STRING
|
2
2
|
|
3
|
-
if version >= '
|
3
|
+
if version >= '5.0.'
|
4
|
+
require_relative 'compat/5.0'
|
5
|
+
elsif version >= '4.2.'
|
4
6
|
require_relative 'compat/4.2'
|
7
|
+
elsif version >= '4.0'
|
8
|
+
require_relative 'compat/4.0'
|
9
|
+
elsif version >= '3.1'
|
10
|
+
require_relative 'compat/3.1'
|
5
11
|
else
|
6
|
-
|
7
|
-
require 'foreigner'
|
8
|
-
rescue LoadError
|
9
|
-
$stderr.puts <<-ERR.strip_heredoc
|
10
|
-
|
11
|
-
ERROR: immigrant requires the foreigner gem (unless you are on rails 4.2+)
|
12
|
-
|
13
|
-
To fix this, add the following to your Gemfile:
|
14
|
-
|
15
|
-
gem "foreigner", "~> 1.2"
|
16
|
-
|
17
|
-
Or just upgrade rails ;) ... lol, "just"
|
18
|
-
|
19
|
-
ERR
|
20
|
-
exit 1
|
21
|
-
end
|
22
|
-
Foreigner.load
|
23
|
-
|
24
|
-
require_relative 'compat/foreigner_extensions'
|
25
|
-
|
26
|
-
if version >= '4.0'
|
27
|
-
require_relative 'compat/4.0'
|
28
|
-
elsif version >= '3.1'
|
29
|
-
require_relative 'compat/3.1'
|
30
|
-
else
|
31
|
-
require_relative 'compat/3.0'
|
32
|
-
end
|
33
|
-
end
|
34
|
-
|
35
|
-
# add some useful things for querying/comparing/dumping foreign keys
|
36
|
-
module Immigrant
|
37
|
-
module ForeignKeyExtensions
|
38
|
-
def initialize(from_table, to_table, options, *args)
|
39
|
-
options ||= {}
|
40
|
-
options[:name] ||= "#{from_table}_#{options[:column]}_fk"
|
41
|
-
super(from_table, to_table, options, *args)
|
42
|
-
end
|
43
|
-
|
44
|
-
def hash_key
|
45
|
-
[from_table, options[:column]]
|
46
|
-
end
|
47
|
-
|
48
|
-
def to_ruby(action = :add)
|
49
|
-
if action == :add
|
50
|
-
dump_foreign_key(self)
|
51
|
-
else
|
52
|
-
"remove_foreign_key #{from_table.inspect}, " \
|
53
|
-
":name => #{options[:name].inspect}"
|
54
|
-
end
|
55
|
-
end
|
56
|
-
end
|
12
|
+
require_relative 'compat/3.0'
|
57
13
|
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
# add some useful things for querying/comparing/dumping foreign keys
|
2
|
+
module Immigrant
|
3
|
+
module ForeignKeyExtensions
|
4
|
+
def initialize(from_table, to_table, options, *args)
|
5
|
+
options ||= {}
|
6
|
+
options[:name] ||= "#{from_table}_#{options[:column]}_fk"
|
7
|
+
super(from_table, to_table, options, *args)
|
8
|
+
end
|
9
|
+
|
10
|
+
def hash_key
|
11
|
+
[from_table, options[:column]]
|
12
|
+
end
|
13
|
+
|
14
|
+
def to_ruby(action = :add)
|
15
|
+
if action == :add
|
16
|
+
dump_foreign_key(self)
|
17
|
+
else
|
18
|
+
"remove_foreign_key #{from_table.inspect}, " \
|
19
|
+
":name => #{options[:name].inspect}"
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
data/lib/immigrant.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
require 'active_support/all'
|
2
2
|
|
3
3
|
module Immigrant
|
4
|
-
class
|
4
|
+
class KeyFinder
|
5
5
|
def infer_keys(db_keys = current_foreign_keys, classes = model_classes)
|
6
6
|
database_keys = db_keys.inject({}) { |hash, foreign_key|
|
7
7
|
hash[foreign_key.hash_key] = foreign_key
|
@@ -27,8 +27,12 @@ module Immigrant
|
|
27
27
|
|
28
28
|
private
|
29
29
|
|
30
|
+
def tables
|
31
|
+
@tables ||= ActiveRecord::Base.connection.tables
|
32
|
+
end
|
33
|
+
|
30
34
|
def current_foreign_keys
|
31
|
-
|
35
|
+
tables.map{ |table|
|
32
36
|
ActiveRecord::Base.connection.foreign_keys(table)
|
33
37
|
}.flatten
|
34
38
|
end
|
@@ -81,16 +85,17 @@ module Immigrant
|
|
81
85
|
end
|
82
86
|
|
83
87
|
def foreign_keys_for(klass)
|
88
|
+
return [] if klass.abstract_class? || !tables.include?(klass.table_name)
|
84
89
|
candidate_reflections_for(klass).inject([]) do |result, reflection|
|
85
90
|
begin
|
86
|
-
result.concat
|
91
|
+
result.concat foreign_keys_for_reflection(klass, reflection)
|
87
92
|
rescue NameError # e.g. belongs_to :oops_this_is_not_a_table
|
88
93
|
result
|
89
94
|
end
|
90
95
|
end
|
91
96
|
end
|
92
97
|
|
93
|
-
def
|
98
|
+
def foreign_keys_for_reflection(klass, reflection)
|
94
99
|
case reflection.macro
|
95
100
|
when :belongs_to
|
96
101
|
infer_belongs_to_keys(klass, reflection)
|
@@ -98,59 +103,112 @@ module Immigrant
|
|
98
103
|
infer_has_n_keys(klass, reflection)
|
99
104
|
when :has_and_belongs_to_many
|
100
105
|
infer_habtm_keys(klass, reflection)
|
101
|
-
|
102
|
-
[]
|
103
|
-
end
|
106
|
+
end || []
|
104
107
|
end
|
105
108
|
|
106
109
|
def infer_belongs_to_keys(klass, reflection)
|
107
|
-
return
|
110
|
+
return if reflection.name == :left_side # redundant and unusable reflection automagically created by HABTM
|
111
|
+
|
112
|
+
from_table = klass.table_name
|
113
|
+
to_table = reflection.klass.table_name
|
114
|
+
column = reflection.send(FOREIGN_KEY).to_s
|
115
|
+
primary_key = (reflection.options[:primary_key] || reflection.klass.primary_key).to_s
|
116
|
+
|
117
|
+
return unless column_exists?(from_table, column)
|
118
|
+
|
108
119
|
[
|
109
120
|
ForeignKeyDefinition.new(
|
110
|
-
|
111
|
-
|
112
|
-
:column =>
|
113
|
-
:primary_key =>
|
121
|
+
from_table,
|
122
|
+
to_table,
|
123
|
+
:column => column,
|
124
|
+
:primary_key => primary_key
|
114
125
|
# although belongs_to can specify :dependent, it doesn't make
|
115
|
-
# sense from a foreign key perspective
|
116
|
-
ON_DELETE => nil
|
126
|
+
# sense from a foreign key perspective, so no :on_delete
|
117
127
|
)
|
118
128
|
]
|
119
129
|
end
|
120
130
|
|
121
131
|
def infer_has_n_keys(klass, reflection)
|
132
|
+
from_table = reflection.klass.table_name
|
133
|
+
to_table = klass.table_name
|
134
|
+
column = reflection.send(FOREIGN_KEY).to_s
|
135
|
+
primary_key = (reflection.options[:primary_key] || klass.primary_key).to_s
|
136
|
+
|
137
|
+
actions = {}
|
138
|
+
if [:delete, :delete_all].include?(reflection.options[:dependent]) && !qualified_reflection?(reflection, klass)
|
139
|
+
actions = {:on_delete => :cascade, :on_update => :cascade}
|
140
|
+
end
|
141
|
+
|
142
|
+
return unless column_exists?(from_table, column)
|
143
|
+
|
122
144
|
[
|
123
145
|
ForeignKeyDefinition.new(
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
146
|
+
from_table,
|
147
|
+
to_table,
|
148
|
+
{
|
149
|
+
:column => column,
|
150
|
+
:primary_key => primary_key
|
151
|
+
}.merge(actions)
|
129
152
|
)
|
130
153
|
]
|
131
154
|
end
|
132
155
|
|
133
156
|
def infer_habtm_keys(klass, reflection)
|
157
|
+
keys = []
|
158
|
+
|
134
159
|
join_table = (reflection.respond_to?(:join_table) ? reflection.join_table : reflection.options[:join_table]).to_s
|
135
|
-
|
136
|
-
|
160
|
+
|
161
|
+
left_to_table = klass.table_name
|
162
|
+
left_column = reflection.send(FOREIGN_KEY).to_s
|
163
|
+
left_primary_key = klass.primary_key.to_s
|
164
|
+
if column_exists?(join_table, left_column)
|
165
|
+
keys << ForeignKeyDefinition.new(
|
137
166
|
join_table,
|
138
|
-
|
139
|
-
:column =>
|
140
|
-
:primary_key =>
|
141
|
-
|
142
|
-
|
143
|
-
|
167
|
+
left_to_table,
|
168
|
+
:column => left_column,
|
169
|
+
:primary_key => left_primary_key
|
170
|
+
)
|
171
|
+
end
|
172
|
+
|
173
|
+
right_to_table = reflection.klass.table_name
|
174
|
+
right_column = reflection.association_foreign_key.to_s
|
175
|
+
right_primary_key = reflection.klass.primary_key.to_s
|
176
|
+
if column_exists?(join_table, left_column)
|
177
|
+
keys << ForeignKeyDefinition.new(
|
144
178
|
join_table,
|
145
|
-
|
146
|
-
:column =>
|
147
|
-
:primary_key =>
|
148
|
-
ON_DELETE => nil
|
179
|
+
right_to_table,
|
180
|
+
:column => right_column,
|
181
|
+
:primary_key => right_primary_key
|
149
182
|
)
|
150
|
-
|
183
|
+
end
|
184
|
+
|
185
|
+
keys
|
186
|
+
end
|
187
|
+
|
188
|
+
def column_exists?(table_name, column_name)
|
189
|
+
columns_for(table_name).any? { |column| column.name == column_name }
|
190
|
+
end
|
191
|
+
|
192
|
+
def columns_for(table_name)
|
193
|
+
@columns ||= {}
|
194
|
+
@columns[table_name] ||= ActiveRecord::Base.connection.columns(table_name)
|
195
|
+
end
|
196
|
+
|
197
|
+
def qualified_reflection?(reflection, klass)
|
198
|
+
scope = reflection.scope
|
199
|
+
if scope.nil?
|
200
|
+
false
|
201
|
+
else
|
202
|
+
klass.instance_exec(*([nil]*scope.arity), &scope).where_clause.any?
|
203
|
+
end
|
204
|
+
rescue
|
205
|
+
# if there's an error evaluating the scope block or whatever, just
|
206
|
+
# err on the side of caution and assume there are conditions
|
207
|
+
true
|
151
208
|
end
|
152
209
|
end
|
153
210
|
end
|
154
211
|
|
155
212
|
require 'immigrant/loader'
|
213
|
+
require 'immigrant/foreign_key_extensions'
|
156
214
|
require 'immigrant/railtie' if defined?(Rails)
|
data/test/helper.rb
CHANGED
data/test/immigrant_test.rb
CHANGED
@@ -3,22 +3,19 @@ require 'helper'
|
|
3
3
|
class ImmigrantTest < ActiveSupport::TestCase
|
4
4
|
include TestMethods
|
5
5
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
def connection
|
13
|
-
@connection ||= MockConnection.new
|
14
|
-
end
|
6
|
+
ActiveRecord::Base.instance_eval do
|
7
|
+
def primary_key
|
8
|
+
connection.primary_key(table_name)
|
9
|
+
end
|
10
|
+
def connection
|
11
|
+
@connection ||= MockConnection.new
|
15
12
|
end
|
16
13
|
|
17
14
|
if ActiveRecord::VERSION::STRING >= '4.'
|
18
15
|
# support old 3.x syntax for the sake of concise tests
|
19
|
-
|
20
|
-
|
21
|
-
|
16
|
+
extend(Module.new{
|
17
|
+
[:belongs_to, :has_one, :has_many, :has_and_belongs_to_many].each do |method|
|
18
|
+
define_method method do |assoc, scope = nil, options = {}|
|
22
19
|
if scope.is_a?(Hash)
|
23
20
|
options = scope
|
24
21
|
scope_opts = options.extract!(:conditions, :order)
|
@@ -28,8 +25,8 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
28
25
|
end
|
29
26
|
super assoc, scope, options
|
30
27
|
end
|
31
|
-
|
32
|
-
|
28
|
+
end
|
29
|
+
})
|
33
30
|
end
|
34
31
|
end
|
35
32
|
|
@@ -40,18 +37,27 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
40
37
|
def primary_key(table)
|
41
38
|
table.to_s !~ /s_.*s\z/ ? 'id' : nil
|
42
39
|
end
|
40
|
+
def tables
|
41
|
+
ActiveSupport::DescendantsTracker.direct_descendants(ActiveRecord::Base).map(&:table_name)
|
42
|
+
end
|
43
|
+
def columns(table_name)
|
44
|
+
AnyColumn.new
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
class AnyColumn
|
49
|
+
def any?
|
50
|
+
true
|
51
|
+
end
|
43
52
|
end
|
44
53
|
|
45
54
|
def teardown
|
46
|
-
subclasses = ActiveSupport::DescendantsTracker.direct_descendants(
|
55
|
+
subclasses = ActiveSupport::DescendantsTracker.direct_descendants(ActiveRecord::Base)
|
47
56
|
subclasses.each do |subclass|
|
48
|
-
|
57
|
+
subclass = subclass.to_s
|
58
|
+
Object.send(:remove_const, subclass) if subclass =~ /\A[A-Z]/ && Object.const_defined?(subclass)
|
49
59
|
end
|
50
60
|
subclasses.replace([])
|
51
|
-
# also need to clear out other things under AR::Base, because as of
|
52
|
-
# 4.1 there are automagical anonymous classes due to HABTM
|
53
|
-
subclasses = ActiveSupport::DescendantsTracker.direct_descendants(ActiveRecord::Base)
|
54
|
-
subclasses.replace([MockModel])
|
55
61
|
end
|
56
62
|
|
57
63
|
def given(code)
|
@@ -60,194 +66,183 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
60
66
|
Object.class_eval code
|
61
67
|
end
|
62
68
|
|
69
|
+
def infer_keys(db_keys = [])
|
70
|
+
keys = Immigrant::KeyFinder.new.infer_keys(db_keys).first
|
71
|
+
# ensure each key generates correctly
|
72
|
+
keys.each { |key| key.to_ruby(:add) }
|
73
|
+
keys.sort_by { |key| [key.from_table, key.to_table] }
|
74
|
+
end
|
75
|
+
|
63
76
|
# basic scenarios
|
64
77
|
|
65
78
|
test 'belongs_to should generate a foreign key' do
|
66
79
|
given <<-CODE
|
67
|
-
class Author <
|
68
|
-
class Book <
|
80
|
+
class Author < ActiveRecord::Base; end
|
81
|
+
class Book < ActiveRecord::Base
|
69
82
|
belongs_to :guy, :class_name => 'Author', :foreign_key => 'author_id'
|
70
83
|
end
|
71
84
|
CODE
|
72
85
|
|
73
|
-
keys = Immigrant.infer_keys([]).first
|
74
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
75
86
|
assert_equal(
|
76
87
|
[foreign_key_definition(
|
77
88
|
'books', 'authors',
|
78
|
-
:column => 'author_id', :primary_key => 'id'
|
89
|
+
:column => 'author_id', :primary_key => 'id'
|
79
90
|
)],
|
80
|
-
|
91
|
+
infer_keys
|
81
92
|
)
|
82
93
|
end
|
83
94
|
|
84
95
|
test 'has_one should generate a foreign key' do
|
85
96
|
given <<-CODE
|
86
|
-
class Author <
|
97
|
+
class Author < ActiveRecord::Base
|
87
98
|
has_one :piece_de_resistance, :class_name => 'Book', :order => "id DESC"
|
88
99
|
end
|
89
|
-
class Book <
|
100
|
+
class Book < ActiveRecord::Base; end
|
90
101
|
CODE
|
91
102
|
|
92
|
-
keys = Immigrant.infer_keys([]).first
|
93
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
94
103
|
assert_equal(
|
95
104
|
[foreign_key_definition(
|
96
105
|
'books', 'authors',
|
97
|
-
:column => 'author_id', :primary_key => 'id'
|
106
|
+
:column => 'author_id', :primary_key => 'id'
|
98
107
|
)],
|
99
|
-
|
108
|
+
infer_keys
|
100
109
|
)
|
101
110
|
end
|
102
111
|
|
103
|
-
test 'has_one :dependent => :delete should generate a foreign key with :on_delete => :
|
112
|
+
test 'has_one :dependent => :delete should generate a foreign key with :on_delete => :cascade' do
|
104
113
|
given <<-CODE
|
105
|
-
class Author <
|
114
|
+
class Author < ActiveRecord::Base
|
106
115
|
has_one :book, :order => "id DESC", :dependent => :delete
|
107
116
|
end
|
108
|
-
class Book <
|
117
|
+
class Book < ActiveRecord::Base; end
|
109
118
|
CODE
|
110
119
|
|
111
|
-
keys = Immigrant.infer_keys([]).first
|
112
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
113
120
|
assert_equal(
|
114
121
|
[foreign_key_definition(
|
115
122
|
'books', 'authors',
|
116
|
-
:column => 'author_id', :primary_key => 'id',
|
123
|
+
:column => 'author_id', :primary_key => 'id', :on_delete => :cascade, :on_update => :cascade
|
117
124
|
)],
|
118
|
-
|
125
|
+
infer_keys
|
119
126
|
)
|
120
127
|
end
|
121
128
|
|
122
129
|
test 'has_many should generate a foreign key' do
|
123
130
|
given <<-CODE
|
124
|
-
class Author <
|
131
|
+
class Author < ActiveRecord::Base
|
125
132
|
has_many :babies, :class_name => 'Book'
|
126
133
|
end
|
127
|
-
class Book <
|
134
|
+
class Book < ActiveRecord::Base; end
|
128
135
|
CODE
|
129
136
|
|
130
|
-
keys = Immigrant.infer_keys([]).first
|
131
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
132
137
|
assert_equal(
|
133
138
|
[foreign_key_definition(
|
134
139
|
'books', 'authors',
|
135
|
-
:column => 'author_id', :primary_key => 'id'
|
140
|
+
:column => 'author_id', :primary_key => 'id'
|
136
141
|
)],
|
137
|
-
|
142
|
+
infer_keys
|
138
143
|
)
|
139
144
|
end
|
140
145
|
|
141
|
-
test 'has_many :dependent => :delete_all should generate a foreign key with :on_delete => :
|
146
|
+
test 'has_many :dependent => :delete_all should generate a foreign key with :on_delete => :cascade' do
|
142
147
|
given <<-CODE
|
143
|
-
class Author <
|
148
|
+
class Author < ActiveRecord::Base
|
144
149
|
has_many :books, :dependent => :delete_all
|
145
150
|
end
|
146
|
-
class Book <
|
151
|
+
class Book < ActiveRecord::Base; end
|
147
152
|
CODE
|
148
153
|
|
149
|
-
keys = Immigrant.infer_keys([]).first
|
150
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
151
154
|
assert_equal(
|
152
155
|
[foreign_key_definition(
|
153
156
|
'books', 'authors',
|
154
|
-
:column => 'author_id', :primary_key => 'id',
|
157
|
+
:column => 'author_id', :primary_key => 'id', :on_delete => :cascade, :on_update => :cascade
|
155
158
|
)],
|
156
|
-
|
159
|
+
infer_keys
|
157
160
|
)
|
158
161
|
end
|
159
162
|
|
160
163
|
test 'has_and_belongs_to_many should generate two foreign keys' do
|
161
164
|
given <<-CODE
|
162
|
-
class Author <
|
165
|
+
class Author < ActiveRecord::Base
|
163
166
|
has_and_belongs_to_many :fans
|
164
167
|
end
|
165
|
-
class Fan <
|
168
|
+
class Fan < ActiveRecord::Base; end
|
166
169
|
CODE
|
167
170
|
|
168
|
-
keys = Immigrant.infer_keys([]).first
|
169
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
170
171
|
assert_equal(
|
171
172
|
[foreign_key_definition(
|
172
173
|
'authors_fans', 'authors',
|
173
|
-
:column => 'author_id', :primary_key => 'id'
|
174
|
+
:column => 'author_id', :primary_key => 'id'
|
174
175
|
),
|
175
176
|
foreign_key_definition(
|
176
177
|
'authors_fans', 'fans',
|
177
|
-
:column => 'fan_id', :primary_key => 'id'
|
178
|
+
:column => 'fan_id', :primary_key => 'id'
|
178
179
|
)],
|
179
|
-
|
180
|
+
infer_keys
|
180
181
|
)
|
181
182
|
end
|
182
183
|
|
183
184
|
test 'has_and_belongs_to_many should respect the join_table' do
|
184
185
|
given <<-CODE
|
185
|
-
class Author <
|
186
|
+
class Author < ActiveRecord::Base
|
186
187
|
has_and_belongs_to_many :fans, :join_table => :lols_wuts
|
187
188
|
end
|
188
|
-
class Fan <
|
189
|
+
class Fan < ActiveRecord::Base; end
|
189
190
|
CODE
|
190
191
|
|
191
|
-
keys = Immigrant.infer_keys([]).first
|
192
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
193
192
|
assert_equal(
|
194
193
|
[foreign_key_definition(
|
195
194
|
'lols_wuts', 'authors',
|
196
|
-
:column => 'author_id', :primary_key => 'id'
|
195
|
+
:column => 'author_id', :primary_key => 'id'
|
197
196
|
),
|
198
197
|
foreign_key_definition(
|
199
198
|
'lols_wuts', 'fans',
|
200
|
-
:column => 'fan_id', :primary_key => 'id'
|
199
|
+
:column => 'fan_id', :primary_key => 'id'
|
201
200
|
)],
|
202
|
-
|
201
|
+
infer_keys
|
203
202
|
)
|
204
203
|
end
|
205
204
|
|
206
205
|
test 'conditional has_one/has_many associations should ignore :dependent' do
|
207
206
|
given <<-CODE
|
208
|
-
class Author <
|
207
|
+
class Author < ActiveRecord::Base
|
209
208
|
has_many :articles, :conditions => "published", :dependent => :delete_all
|
210
209
|
has_one :favorite_book, :class_name => 'Book',
|
211
210
|
:conditions => "most_awesome", :dependent => :delete
|
212
211
|
end
|
213
|
-
class Book <
|
214
|
-
class Article <
|
212
|
+
class Book < ActiveRecord::Base; end
|
213
|
+
class Article < ActiveRecord::Base; end
|
215
214
|
CODE
|
216
215
|
|
217
|
-
keys = Immigrant.infer_keys([]).first
|
218
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
219
216
|
assert_equal(
|
220
217
|
[foreign_key_definition(
|
221
218
|
'articles', 'authors',
|
222
|
-
:column => 'author_id', :primary_key => 'id'
|
219
|
+
:column => 'author_id', :primary_key => 'id'
|
223
220
|
),
|
224
221
|
foreign_key_definition(
|
225
222
|
'books', 'authors',
|
226
|
-
:column => 'author_id', :primary_key => 'id'
|
223
|
+
:column => 'author_id', :primary_key => 'id'
|
227
224
|
)],
|
228
|
-
|
225
|
+
infer_keys
|
229
226
|
)
|
230
227
|
end
|
231
228
|
|
232
229
|
test 'primary_key should be respected' do
|
233
230
|
given <<-CODE
|
234
|
-
class User <
|
231
|
+
class User < ActiveRecord::Base
|
235
232
|
has_many :emails, :primary_key => :email, :foreign_key => :to,
|
236
233
|
:dependent => :destroy
|
237
234
|
end
|
238
|
-
class Email <
|
235
|
+
class Email < ActiveRecord::Base
|
239
236
|
belongs_to :user, :primary_key => :email, :foreign_key => :to
|
240
237
|
end
|
241
238
|
CODE
|
242
239
|
|
243
|
-
keys = Immigrant.infer_keys([]).first
|
244
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
245
240
|
assert_equal(
|
246
241
|
[foreign_key_definition(
|
247
242
|
'emails', 'users',
|
248
|
-
:column => 'to', :primary_key => 'email'
|
243
|
+
:column => 'to', :primary_key => 'email'
|
249
244
|
)],
|
250
|
-
|
245
|
+
infer_keys
|
251
246
|
)
|
252
247
|
end
|
253
248
|
|
@@ -255,64 +250,58 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
255
250
|
|
256
251
|
test 'STI should not generate duplicate foreign keys' do
|
257
252
|
given <<-CODE
|
258
|
-
class Company <
|
259
|
-
class Employee <
|
253
|
+
class Company < ActiveRecord::Base; end
|
254
|
+
class Employee < ActiveRecord::Base
|
260
255
|
belongs_to :company
|
261
256
|
end
|
262
257
|
class Manager < Employee; end
|
263
258
|
CODE
|
264
259
|
|
265
260
|
assert(Manager.reflections.present?)
|
266
|
-
keys = Immigrant.infer_keys([]).first
|
267
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
268
261
|
assert_equal(
|
269
262
|
[foreign_key_definition(
|
270
263
|
'employees', 'companies',
|
271
|
-
:column => 'company_id', :primary_key => 'id'
|
264
|
+
:column => 'company_id', :primary_key => 'id'
|
272
265
|
)],
|
273
|
-
|
266
|
+
infer_keys
|
274
267
|
)
|
275
268
|
end
|
276
269
|
|
277
270
|
test 'complementary associations should not generate duplicate foreign keys' do
|
278
271
|
given <<-CODE
|
279
|
-
class Author <
|
272
|
+
class Author < ActiveRecord::Base
|
280
273
|
has_many :books
|
281
274
|
end
|
282
|
-
class Book <
|
275
|
+
class Book < ActiveRecord::Base
|
283
276
|
belongs_to :author
|
284
277
|
end
|
285
278
|
CODE
|
286
279
|
|
287
|
-
keys = Immigrant.infer_keys([]).first
|
288
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
289
280
|
assert_equal(
|
290
281
|
[foreign_key_definition(
|
291
282
|
'books', 'authors',
|
292
|
-
:column => 'author_id', :primary_key => 'id'
|
283
|
+
:column => 'author_id', :primary_key => 'id'
|
293
284
|
)],
|
294
|
-
|
285
|
+
infer_keys
|
295
286
|
)
|
296
287
|
end
|
297
288
|
|
298
289
|
test 'redundant associations should not generate duplicate foreign keys' do
|
299
290
|
given <<-CODE
|
300
|
-
class Author <
|
291
|
+
class Author < ActiveRecord::Base
|
301
292
|
has_many :books
|
302
293
|
has_many :favorite_books, :class_name => 'Book', :conditions => "awesome"
|
303
294
|
has_many :bad_books, :class_name => 'Book', :conditions => "amateur_hour"
|
304
295
|
end
|
305
|
-
class Book <
|
296
|
+
class Book < ActiveRecord::Base; end
|
306
297
|
CODE
|
307
298
|
|
308
|
-
keys = Immigrant.infer_keys([]).first
|
309
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
310
299
|
assert_equal(
|
311
300
|
[foreign_key_definition(
|
312
301
|
'books', 'authors',
|
313
|
-
:column => 'author_id', :primary_key => 'id'
|
302
|
+
:column => 'author_id', :primary_key => 'id'
|
314
303
|
)],
|
315
|
-
|
304
|
+
infer_keys
|
316
305
|
)
|
317
306
|
end
|
318
307
|
|
@@ -323,33 +312,32 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
323
312
|
database_keys = [
|
324
313
|
foreign_key_definition(
|
325
314
|
'articles', 'authors',
|
326
|
-
:column => 'author_id', :primary_key => 'id',
|
315
|
+
:column => 'author_id', :primary_key => 'id',
|
327
316
|
:name => "doesn't_matter"
|
328
317
|
),
|
329
318
|
foreign_key_definition(
|
330
319
|
'books', 'authors', :column => 'author_id', :primary_key => 'id',
|
331
|
-
|
320
|
+
:on_delete => :restrict, :on_update => :nullify
|
332
321
|
)
|
333
322
|
]
|
334
323
|
|
335
324
|
given <<-CODE
|
336
|
-
class Author <
|
325
|
+
class Author < ActiveRecord::Base
|
337
326
|
has_many :articles
|
338
327
|
has_one :favorite_book, :class_name => 'Book',
|
339
328
|
:conditions => "most_awesome"
|
340
329
|
end
|
341
|
-
class Book <
|
342
|
-
class Article <
|
330
|
+
class Book < ActiveRecord::Base; end
|
331
|
+
class Article < ActiveRecord::Base; end
|
343
332
|
CODE
|
344
333
|
|
345
|
-
|
346
|
-
assert_equal([], keys)
|
334
|
+
assert_equal([], infer_keys(database_keys))
|
347
335
|
end
|
348
336
|
|
349
337
|
if ActiveRecord::VERSION::STRING < '4.'
|
350
338
|
test 'finder_sql associations should not generate foreign keys' do
|
351
339
|
given <<-CODE
|
352
|
-
class Author <
|
340
|
+
class Author < ActiveRecord::Base
|
353
341
|
has_many :books, :finder_sql => <<-SQL
|
354
342
|
SELECT *
|
355
343
|
FROM books
|
@@ -357,79 +345,113 @@ class ImmigrantTest < ActiveSupport::TestCase
|
|
357
345
|
ORDER BY RANDOM() LIMIT 5'
|
358
346
|
SQL
|
359
347
|
end
|
360
|
-
class Book <
|
348
|
+
class Book < ActiveRecord::Base; end
|
361
349
|
CODE
|
362
350
|
|
363
|
-
|
364
|
-
assert_equal([], keys)
|
351
|
+
assert_equal([], infer_keys)
|
365
352
|
end
|
366
353
|
end
|
367
354
|
|
368
355
|
test 'polymorphic associations should not generate foreign keys' do
|
369
356
|
given <<-CODE
|
370
|
-
class Property <
|
357
|
+
class Property < ActiveRecord::Base
|
371
358
|
belongs_to :owner, :polymorphic => true
|
372
359
|
end
|
373
|
-
class Person <
|
360
|
+
class Person < ActiveRecord::Base
|
374
361
|
has_many :properties, :as => :owner
|
375
362
|
end
|
376
|
-
class Corporation <
|
363
|
+
class Corporation < ActiveRecord::Base
|
377
364
|
has_many :properties, :as => :owner
|
378
365
|
end
|
379
366
|
CODE
|
380
367
|
|
381
|
-
|
382
|
-
assert_equal([], keys)
|
368
|
+
assert_equal([], infer_keys)
|
383
369
|
end
|
384
370
|
|
385
371
|
test 'has_many :through should not generate foreign keys' do
|
386
372
|
given <<-CODE
|
387
|
-
class Author <
|
373
|
+
class Author < ActiveRecord::Base
|
388
374
|
has_many :authors_fans
|
389
375
|
has_many :fans, :through => :authors_fans
|
390
376
|
end
|
391
|
-
class AuthorsFan <
|
377
|
+
class AuthorsFan < ActiveRecord::Base
|
392
378
|
belongs_to :author
|
393
379
|
belongs_to :fan
|
394
380
|
end
|
395
|
-
class Fan <
|
381
|
+
class Fan < ActiveRecord::Base
|
396
382
|
has_many :authors_fans
|
397
383
|
has_many :authors, :through => :authors_fans
|
398
384
|
end
|
399
385
|
CODE
|
400
386
|
|
401
|
-
keys = Immigrant.infer_keys([]).first
|
402
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
403
387
|
assert_equal(
|
404
388
|
[foreign_key_definition(
|
405
389
|
'authors_fans', 'authors',
|
406
|
-
:column => 'author_id', :primary_key => 'id'
|
390
|
+
:column => 'author_id', :primary_key => 'id'
|
407
391
|
),
|
408
392
|
foreign_key_definition(
|
409
393
|
'authors_fans', 'fans',
|
410
|
-
:column => 'fan_id', :primary_key => 'id'
|
394
|
+
:column => 'fan_id', :primary_key => 'id'
|
411
395
|
)],
|
412
|
-
|
396
|
+
infer_keys
|
413
397
|
)
|
414
398
|
end
|
415
399
|
|
416
400
|
test 'broken associations should not cause errors' do
|
417
401
|
given <<-CODE
|
418
|
-
class Author <
|
419
|
-
class Book <
|
402
|
+
class Author < ActiveRecord::Base; end
|
403
|
+
class Book < ActiveRecord::Base
|
420
404
|
belongs_to :author
|
421
405
|
belongs_to :invalid
|
422
406
|
end
|
423
407
|
CODE
|
424
408
|
|
425
|
-
keys = Immigrant.infer_keys([]).first
|
426
|
-
assert_nothing_raised { keys.map { |key| key.to_ruby(:add) } }
|
427
409
|
assert_equal(
|
428
410
|
[foreign_key_definition(
|
429
411
|
'books', 'authors',
|
430
|
-
:column => 'author_id', :primary_key => 'id'
|
412
|
+
:column => 'author_id', :primary_key => 'id'
|
431
413
|
)],
|
432
|
-
|
414
|
+
infer_keys
|
433
415
|
)
|
434
416
|
end
|
417
|
+
|
418
|
+
test 'abstract classes should not generate a foreign key' do
|
419
|
+
given <<-CODE
|
420
|
+
class User < ActiveRecord::Base; end
|
421
|
+
class Widget < ActiveRecord::Base
|
422
|
+
self.abstract_class = true
|
423
|
+
|
424
|
+
belongs_to :user
|
425
|
+
end
|
426
|
+
CODE
|
427
|
+
|
428
|
+
assert_equal([], infer_keys)
|
429
|
+
end
|
430
|
+
|
431
|
+
test 'missing tables should not generate a foreign key' do
|
432
|
+
given <<-CODE
|
433
|
+
class User < ActiveRecord::Base; end
|
434
|
+
class Widget < ActiveRecord::Base
|
435
|
+
self.table_name = :wiiiidgets
|
436
|
+
belongs_to :user
|
437
|
+
end
|
438
|
+
CODE
|
439
|
+
|
440
|
+
MockConnection.stub_any_instance(:tables, ["users"]) do
|
441
|
+
assert_equal([], infer_keys)
|
442
|
+
end
|
443
|
+
end
|
444
|
+
|
445
|
+
test 'invalid columns should not generate a foreign key' do
|
446
|
+
given <<-CODE
|
447
|
+
class User < ActiveRecord::Base; end
|
448
|
+
class Widget < ActiveRecord::Base
|
449
|
+
belongs_to :user
|
450
|
+
end
|
451
|
+
CODE
|
452
|
+
|
453
|
+
MockConnection.stub_any_instance(:columns, []) do
|
454
|
+
assert_equal([], infer_keys)
|
455
|
+
end
|
456
|
+
end
|
435
457
|
end
|
metadata
CHANGED
@@ -1,30 +1,27 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: immigrant
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
5
|
-
prerelease:
|
4
|
+
version: 0.3.0
|
6
5
|
platform: ruby
|
7
6
|
authors:
|
8
7
|
- Jon Jensen
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
date:
|
11
|
+
date: 2015-02-24 00:00:00.000000000 Z
|
13
12
|
dependencies:
|
14
13
|
- !ruby/object:Gem::Dependency
|
15
14
|
name: activerecord
|
16
15
|
requirement: !ruby/object:Gem::Requirement
|
17
|
-
none: false
|
18
16
|
requirements:
|
19
|
-
- -
|
17
|
+
- - ">="
|
20
18
|
- !ruby/object:Gem::Version
|
21
19
|
version: '3.0'
|
22
20
|
type: :runtime
|
23
21
|
prerelease: false
|
24
22
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
-
none: false
|
26
23
|
requirements:
|
27
|
-
- -
|
24
|
+
- - ">="
|
28
25
|
- !ruby/object:Gem::Version
|
29
26
|
version: '3.0'
|
30
27
|
description: Adds a generator for creating a foreign key migration based on your current
|
@@ -35,47 +32,48 @@ extensions: []
|
|
35
32
|
extra_rdoc_files: []
|
36
33
|
files:
|
37
34
|
- LICENSE.txt
|
38
|
-
- Rakefile
|
39
35
|
- README.md
|
36
|
+
- Rakefile
|
40
37
|
- lib/generators/USAGE
|
41
38
|
- lib/generators/immigration_generator.rb
|
42
39
|
- lib/generators/templates/immigration-pre-3.1.rb.erb
|
43
40
|
- lib/generators/templates/immigration.rb.erb
|
41
|
+
- lib/immigrant.rb
|
42
|
+
- lib/immigrant/compat.rb
|
44
43
|
- lib/immigrant/compat/3.0.rb
|
45
44
|
- lib/immigrant/compat/3.1.rb
|
46
45
|
- lib/immigrant/compat/4.0.rb
|
47
46
|
- lib/immigrant/compat/4.2.rb
|
48
|
-
- lib/immigrant/compat/
|
49
|
-
- lib/immigrant/compat.rb
|
47
|
+
- lib/immigrant/compat/5.0.rb
|
48
|
+
- lib/immigrant/compat/active_record.rb
|
49
|
+
- lib/immigrant/compat/foreigner.rb
|
50
|
+
- lib/immigrant/foreign_key_extensions.rb
|
50
51
|
- lib/immigrant/loader.rb
|
51
52
|
- lib/immigrant/railtie.rb
|
52
|
-
- lib/immigrant.rb
|
53
53
|
- test/compat.rb
|
54
54
|
- test/helper.rb
|
55
55
|
- test/immigrant_test.rb
|
56
56
|
homepage: http://github.com/jenseng/immigrant
|
57
57
|
licenses: []
|
58
|
+
metadata: {}
|
58
59
|
post_install_message:
|
59
60
|
rdoc_options: []
|
60
61
|
require_paths:
|
61
62
|
- lib
|
62
63
|
required_ruby_version: !ruby/object:Gem::Requirement
|
63
|
-
none: false
|
64
64
|
requirements:
|
65
|
-
- -
|
65
|
+
- - ">="
|
66
66
|
- !ruby/object:Gem::Version
|
67
67
|
version: 1.8.7
|
68
68
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
69
|
-
none: false
|
70
69
|
requirements:
|
71
|
-
- -
|
70
|
+
- - ">="
|
72
71
|
- !ruby/object:Gem::Version
|
73
72
|
version: 1.3.5
|
74
73
|
requirements: []
|
75
74
|
rubyforge_project:
|
76
|
-
rubygems_version:
|
75
|
+
rubygems_version: 2.2.2
|
77
76
|
signing_key:
|
78
|
-
specification_version:
|
77
|
+
specification_version: 4
|
79
78
|
summary: Foreign key migration generator for Rails
|
80
79
|
test_files: []
|
81
|
-
has_rdoc:
|