matthuhiggins-foreigner 0.2.1 → 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.
- data/README +1 -1
- data/lib/foreigner/connection_adapters/abstract/schema_definitions.rb +4 -0
- data/lib/foreigner/connection_adapters/abstract/schema_statements.rb +3 -0
- data/lib/foreigner/connection_adapters/mysql_adapter.rb +15 -8
- data/lib/foreigner/connection_adapters/postgresql_adapter.rb +26 -16
- data/lib/foreigner/connection_adapters/sql_2003.rb +2 -11
- data/lib/foreigner/schema_dumper.rb +7 -1
- data/lib/foreigner.rb +2 -1
- metadata +5 -6
data/README
CHANGED
@@ -16,7 +16,7 @@ Install as a plugin:
|
|
16
16
|
|
17
17
|
Install as a gem by adding the following to environment.rb:
|
18
18
|
|
19
|
-
config.gem "matthuhiggins-foreigner", :lib => "foreigner"
|
19
|
+
config.gem "matthuhiggins-foreigner", :lib => "foreigner", :source => http://gemcutter.org
|
20
20
|
|
21
21
|
API
|
22
22
|
---
|
@@ -66,6 +66,8 @@ module Foreigner
|
|
66
66
|
# t.foreign_key(:people, :column => :sender_id)
|
67
67
|
# ====== Creating a named foreign key
|
68
68
|
# t.foreign_key(:people, :column => :sender_id, :name => 'sender_foreign_key')
|
69
|
+
# ====== Defining the column of the +to_table+.
|
70
|
+
# t.foreign_key(:people, :column => :sender_id, :primary_key => :person_id)
|
69
71
|
def foreign_key(to_table, options = {})
|
70
72
|
if @base.supports_foreign_keys?
|
71
73
|
to_table = to_table.to_s.pluralize if ActiveRecord::Base.pluralize_table_names
|
@@ -105,6 +107,8 @@ module Foreigner
|
|
105
107
|
# t.foreign_key(:people, :column => :sender_id)
|
106
108
|
# ====== Creating a named foreign key
|
107
109
|
# t.foreign_key(:people, :column => :sender_id, :name => 'sender_foreign_key')
|
110
|
+
# ====== Defining the column of the +to_table+.
|
111
|
+
# t.foreign_key(:people, :column => :sender_id, :primary_key => :person_id)
|
108
112
|
def foreign_key(to_table, options = {})
|
109
113
|
@base.add_foreign_key(@table_name, to_table, options)
|
110
114
|
end
|
@@ -43,6 +43,9 @@ module Foreigner
|
|
43
43
|
# Specify the column name on the from_table that references the to_table. By default this is guessed
|
44
44
|
# to be the singular name of the to_table with "_id" suffixed. So a to_table of :posts will use "post_id"
|
45
45
|
# as the default <tt>:column</tt>.
|
46
|
+
# [:primary_key]
|
47
|
+
# Specify the column name on the to_table that is referenced by this foreign key. By default this is
|
48
|
+
# assumed to be "id".
|
46
49
|
# [:name]
|
47
50
|
# Specify the name of the foreign key constraint. This defaults to use from_table and foreign key column.
|
48
51
|
# [:dependent]
|
@@ -1,14 +1,22 @@
|
|
1
|
-
require 'foreigner/connection_adapters/sql_2003'
|
2
|
-
|
3
1
|
module Foreigner
|
4
2
|
module ConnectionAdapters
|
5
3
|
module MysqlAdapter
|
6
4
|
include Foreigner::ConnectionAdapters::Sql2003
|
7
5
|
|
6
|
+
def remove_foreign_key(table, options)
|
7
|
+
if Hash === options
|
8
|
+
foreign_key_name = foreign_key_name(table, options[:column], options)
|
9
|
+
else
|
10
|
+
foreign_key_name = foreign_key_name(table, "#{options.to_s.singularize}_id")
|
11
|
+
end
|
12
|
+
|
13
|
+
execute "ALTER TABLE #{quote_table_name(table)} DROP FOREIGN KEY #{quote_column_name(foreign_key_name)}"
|
14
|
+
end
|
15
|
+
|
8
16
|
def foreign_keys(table_name)
|
9
|
-
foreign_keys = []
|
10
17
|
fk_info = select_all %{
|
11
18
|
SELECT fk.referenced_table_name as 'to_table'
|
19
|
+
,fk.referenced_column_name as 'primary_key'
|
12
20
|
,fk.column_name as 'column'
|
13
21
|
,fk.constraint_name as 'name'
|
14
22
|
FROM information_schema.key_column_usage fk
|
@@ -19,8 +27,9 @@ module Foreigner
|
|
19
27
|
|
20
28
|
create_table_info = select_one("SHOW CREATE TABLE #{quote_table_name(table_name)}")["Create Table"]
|
21
29
|
|
22
|
-
fk_info.
|
23
|
-
options = {:column => row['column'], :name => row['name']}
|
30
|
+
fk_info.map do |row|
|
31
|
+
options = {:column => row['column'], :name => row['name'], :primary_key => row['primary_key']}
|
32
|
+
|
24
33
|
if create_table_info =~ /CONSTRAINT #{quote_column_name(row['name'])} FOREIGN KEY .* REFERENCES .* ON DELETE (CASCADE|SET NULL)/
|
25
34
|
if $1 == 'CASCADE'
|
26
35
|
options[:dependent] = :delete
|
@@ -28,10 +37,8 @@ module Foreigner
|
|
28
37
|
options[:dependent] = :nullify
|
29
38
|
end
|
30
39
|
end
|
31
|
-
|
40
|
+
ForeignKeyDefinition.new(table_name, row['to_table'], options)
|
32
41
|
end
|
33
|
-
|
34
|
-
foreign_keys
|
35
42
|
end
|
36
43
|
end
|
37
44
|
end
|
@@ -1,36 +1,46 @@
|
|
1
|
-
require 'foreigner/connection_adapters/sql_2003'
|
2
|
-
|
3
1
|
module Foreigner
|
4
2
|
module ConnectionAdapters
|
5
3
|
module PostgreSQLAdapter
|
6
4
|
include Foreigner::ConnectionAdapters::Sql2003
|
5
|
+
|
6
|
+
def remove_foreign_key(table, options)
|
7
|
+
if Hash === options
|
8
|
+
foreign_key_name = foreign_key_name(table, options[:column], options)
|
9
|
+
else
|
10
|
+
foreign_key_name = foreign_key_name(table, "#{options.to_s.singularize}_id")
|
11
|
+
end
|
12
|
+
|
13
|
+
execute "ALTER TABLE #{quote_table_name(table)} DROP CONSTRAINT #{quote_column_name(foreign_key_name)}"
|
14
|
+
end
|
7
15
|
|
8
16
|
def foreign_keys(table_name)
|
9
17
|
fk_info = select_all %{
|
10
|
-
|
18
|
+
SELECT tc.constraint_name as name
|
11
19
|
,ccu.table_name as to_table
|
20
|
+
,ccu.column_name as primary_key
|
12
21
|
,kcu.column_name as column
|
13
22
|
,rc.delete_rule as dependency
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
23
|
+
FROM information_schema.table_constraints tc
|
24
|
+
JOIN information_schema.key_column_usage kcu
|
25
|
+
USING (constraint_catalog, constraint_schema, constraint_name)
|
26
|
+
JOIN information_schema.referential_constraints rc
|
27
|
+
USING (constraint_catalog, constraint_schema, constraint_name)
|
28
|
+
JOIN information_schema.constraint_column_usage ccu
|
29
|
+
USING (constraint_catalog, constraint_schema, constraint_name)
|
30
|
+
WHERE tc.constraint_type = 'FOREIGN KEY'
|
31
|
+
AND tc.constraint_catalog = '#{@config[:database]}'
|
32
|
+
AND tc.table_name = '#{table_name}'
|
24
33
|
}
|
25
34
|
|
26
|
-
fk_info.
|
27
|
-
options = {:column => row['column'], :name => row['name']}
|
35
|
+
fk_info.map do |row|
|
36
|
+
options = {:column => row['column'], :name => row['name'], :primary_key => row['primary_key']}
|
37
|
+
|
28
38
|
if row['dependency'] == 'CASCADE'
|
29
39
|
options[:dependent] = :delete
|
30
40
|
elsif row['dependency'] == 'SET NULL'
|
31
41
|
options[:dependent] = :nullify
|
32
42
|
end
|
33
|
-
|
43
|
+
ForeignKeyDefinition.new(table_name, row['to_table'], options)
|
34
44
|
end
|
35
45
|
end
|
36
46
|
end
|
@@ -19,23 +19,14 @@ module Foreigner
|
|
19
19
|
|
20
20
|
def foreign_key_definition(to_table, options = {})
|
21
21
|
column = options[:column] || "#{to_table.to_s.singularize}_id"
|
22
|
+
primary_key = options[:primary_key] || "id"
|
22
23
|
dependency = dependency_sql(options[:dependent])
|
23
24
|
|
24
|
-
sql = "FOREIGN KEY (#{quote_column_name(column)}) REFERENCES #{quote_table_name(to_table)}(
|
25
|
+
sql = "FOREIGN KEY (#{quote_column_name(column)}) REFERENCES #{quote_table_name(to_table)}(#{primary_key})"
|
25
26
|
sql << " #{dependency}" unless dependency.blank?
|
26
27
|
sql
|
27
28
|
end
|
28
29
|
|
29
|
-
def remove_foreign_key(table, options)
|
30
|
-
if Hash === options
|
31
|
-
foreign_key_name = foreign_key_name(table, options[:column], options)
|
32
|
-
else
|
33
|
-
foreign_key_name = foreign_key_name(table, "#{options.to_s.singularize}_id")
|
34
|
-
end
|
35
|
-
|
36
|
-
execute "ALTER TABLE #{quote_table_name(table)} DROP FOREIGN KEY #{quote_column_name(foreign_key_name)}"
|
37
|
-
end
|
38
|
-
|
39
30
|
private
|
40
31
|
def foreign_key_name(table, column, options = {})
|
41
32
|
if options[:name]
|
@@ -21,8 +21,14 @@ module Foreigner
|
|
21
21
|
add_foreign_key_statements = foreign_keys.map do |foreign_key|
|
22
22
|
statement_parts = [ ('add_foreign_key ' + foreign_key.from_table.inspect) ]
|
23
23
|
statement_parts << foreign_key.to_table.inspect
|
24
|
-
statement_parts << (':column => ' + foreign_key.options[:column].inspect)
|
25
24
|
statement_parts << (':name => ' + foreign_key.options[:name].inspect)
|
25
|
+
|
26
|
+
if foreign_key.options[:column] != "#{foreign_key.to_table.singularize}_id"
|
27
|
+
statement_parts << (':column => ' + foreign_key.options[:column].inspect)
|
28
|
+
end
|
29
|
+
if foreign_key.options[:primary_key] != 'id'
|
30
|
+
statement_parts << (':primary_key => ' + foreign_key.options[:primary_key].inspect)
|
31
|
+
end
|
26
32
|
if foreign_key.options[:dependent].present?
|
27
33
|
statement_parts << (':dependent => ' + foreign_key.options[:dependent].inspect)
|
28
34
|
end
|
data/lib/foreigner.rb
CHANGED
@@ -1,5 +1,6 @@
|
|
1
1
|
require 'foreigner/connection_adapters/abstract/schema_statements'
|
2
2
|
require 'foreigner/connection_adapters/abstract/schema_definitions'
|
3
|
+
require 'foreigner/connection_adapters/sql_2003'
|
3
4
|
require 'foreigner/schema_dumper'
|
4
5
|
|
5
6
|
module ActiveRecord
|
@@ -13,7 +14,7 @@ module ActiveRecord
|
|
13
14
|
end
|
14
15
|
|
15
16
|
Base.class_eval do
|
16
|
-
if
|
17
|
+
if %w(MySQL PostgreSQL).include? connection.adapter_name
|
17
18
|
require "foreigner/connection_adapters/#{connection.adapter_name.downcase}_adapter"
|
18
19
|
end
|
19
20
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: matthuhiggins-foreigner
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Matthew Higgins
|
@@ -26,9 +26,7 @@ files:
|
|
26
26
|
- Rakefile
|
27
27
|
- README
|
28
28
|
- lib/foreigner.rb
|
29
|
-
- lib/foreigner
|
30
29
|
- lib/foreigner/schema_dumper.rb
|
31
|
-
- lib/foreigner/connection_adapters
|
32
30
|
- lib/foreigner/connection_adapters/sql_2003.rb
|
33
31
|
- lib/foreigner/connection_adapters/mysql_adapter.rb
|
34
32
|
- lib/foreigner/connection_adapters/postgresql_adapter.rb
|
@@ -36,9 +34,10 @@ files:
|
|
36
34
|
- lib/foreigner/connection_adapters/abstract/schema_statements.rb
|
37
35
|
- test/helper.rb
|
38
36
|
- test/mysql_adapter_test.rb
|
39
|
-
has_rdoc:
|
37
|
+
has_rdoc: true
|
40
38
|
homepage: http://github.com/matthuhiggins/foreigner/tree/master
|
41
|
-
licenses:
|
39
|
+
licenses: []
|
40
|
+
|
42
41
|
post_install_message:
|
43
42
|
rdoc_options:
|
44
43
|
- --line-numbers
|
@@ -60,7 +59,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
60
59
|
version:
|
61
60
|
requirements: []
|
62
61
|
|
63
|
-
rubyforge_project:
|
62
|
+
rubyforge_project:
|
64
63
|
rubygems_version: 1.3.5
|
65
64
|
signing_key:
|
66
65
|
specification_version: 1
|