migration_comments 0.3.2 → 0.4.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +2 -1
- data/.travis.yml +27 -0
- data/README.rdoc +12 -3
- data/Rakefile +24 -0
- data/docker-compose.yml +12 -0
- data/gemfiles/rails4.gemfile +4 -0
- data/gemfiles/rails5.gemfile +4 -0
- data/lib/migration_comments.rb +12 -40
- data/lib/migration_comments/active_record/connection_adapters/abstract_adapter.rb +1 -10
- data/lib/migration_comments/active_record/connection_adapters/abstract_adapter/schema_creation.rb +22 -25
- data/lib/migration_comments/active_record/connection_adapters/alter_table.rb +5 -10
- data/lib/migration_comments/active_record/connection_adapters/column.rb +1 -5
- data/lib/migration_comments/active_record/connection_adapters/comment_definition.rb +1 -9
- data/lib/migration_comments/active_record/connection_adapters/mysql2_adapter.rb +97 -3
- data/lib/migration_comments/active_record/connection_adapters/postgresql_adapter.rb +19 -22
- data/lib/migration_comments/active_record/connection_adapters/sqlite3_adapter.rb +73 -46
- data/lib/migration_comments/active_record/connection_adapters/table.rb +3 -3
- data/lib/migration_comments/active_record/connection_adapters/table_definition.rb +9 -18
- data/lib/migration_comments/active_record/schema_dumper.rb +6 -10
- data/lib/migration_comments/annotate_models.rb +6 -8
- data/lib/migration_comments/schema_formatter.rb +8 -1
- data/lib/migration_comments/version.rb +1 -1
- data/migration_comments.gemspec +3 -10
- data/test/add_comments_test.rb +43 -2
- data/test/annotate_models_test.rb +6 -4
- data/test/auto_increment_test.rb +39 -9
- data/test/config/database.yml +2 -2
- data/test/primary_uuid_test.rb +27 -0
- data/test/schema_dumper_test.rb +35 -11
- data/test/test_helper.rb +8 -1
- metadata +34 -11
- data/lib/migration_comments/active_record/connection_adapters/abstract_sqlite_adapter.rb +0 -85
- data/lib/migration_comments/active_record/connection_adapters/mysql_adapter.rb +0 -107
- data/lib/migration_comments/active_record/connection_adapters/sqlite_adapter.rb +0 -71
@@ -1,12 +1,5 @@
|
|
1
1
|
module MigrationComments::ActiveRecord::ConnectionAdapters
|
2
2
|
module PostgreSQLAdapter
|
3
|
-
def self.included(base)
|
4
|
-
base.class_eval do
|
5
|
-
alias_method_chain :create_table, :migration_comments
|
6
|
-
alias_method_chain :add_column, :migration_comments
|
7
|
-
alias_method_chain :change_column, :migration_comments
|
8
|
-
end
|
9
|
-
end
|
10
3
|
|
11
4
|
def comments_supported?
|
12
5
|
true
|
@@ -18,48 +11,52 @@ module MigrationComments::ActiveRecord::ConnectionAdapters
|
|
18
11
|
|
19
12
|
# Set a comment on a table
|
20
13
|
def set_table_comment(table_name, comment_text)
|
21
|
-
execute CommentDefinition.new(
|
14
|
+
execute comment_sql(CommentDefinition.new(table_name, nil, comment_text))
|
22
15
|
end
|
23
16
|
|
24
17
|
# Set a comment on a column
|
25
18
|
def set_column_comment(table_name, column_name, comment_text)
|
26
|
-
execute CommentDefinition.new(
|
19
|
+
execute comment_sql(CommentDefinition.new(table_name, column_name, comment_text))
|
20
|
+
end
|
21
|
+
|
22
|
+
if ::ActiveRecord::VERSION::MAJOR >= 5
|
23
|
+
def change_column_comment(table_name, column_name, comment)
|
24
|
+
comment_text = comment.respond_to?(:comment_text) ? comment.comment_text : comment
|
25
|
+
super(table_name, column_name, comment_text)
|
26
|
+
end
|
27
27
|
end
|
28
28
|
|
29
29
|
def retrieve_table_comment(table_name)
|
30
|
-
|
31
|
-
result[0].nil? ? nil : result[0][0]
|
30
|
+
select_value(table_comment_sql(table_name)).presence
|
32
31
|
end
|
33
32
|
|
34
33
|
def retrieve_column_comments(table_name, *column_names)
|
35
34
|
result = select_rows(column_comment_sql(table_name, *column_names))
|
36
|
-
|
37
|
-
return result.inject({}){|m, row| m[row[0].to_sym] = row[1]; m}
|
35
|
+
Hash[result.map{|row| [row[0].to_sym, row[1].presence]}]
|
38
36
|
end
|
39
37
|
|
40
|
-
def
|
38
|
+
def create_table(table_name, options = {})
|
41
39
|
local_table_definition = nil
|
42
|
-
|
40
|
+
super(table_name, options) do |td|
|
43
41
|
local_table_definition = td
|
44
|
-
local_table_definition.
|
45
|
-
local_table_definition.comment options[:comment] if options.has_key?(:comment)
|
42
|
+
local_table_definition.comment = options[:comment] if options.has_key?(:comment)
|
46
43
|
yield td if block_given?
|
47
44
|
end
|
48
45
|
comments = local_table_definition.collect_comments(table_name)
|
49
46
|
comments.each do |comment_definition|
|
50
|
-
execute comment_definition
|
47
|
+
execute comment_sql(comment_definition)
|
51
48
|
end
|
52
49
|
end
|
53
50
|
|
54
|
-
def
|
55
|
-
|
51
|
+
def add_column(table_name, column_name, type, options = {})
|
52
|
+
super(table_name, column_name, type, options)
|
56
53
|
if options[:comment]
|
57
54
|
set_column_comment(table_name, column_name, options[:comment])
|
58
55
|
end
|
59
56
|
end
|
60
57
|
|
61
|
-
def
|
62
|
-
|
58
|
+
def change_column(table_name, column_name, type, options = {})
|
59
|
+
super(table_name, column_name, type, options)
|
63
60
|
if options.keys.include?(:comment)
|
64
61
|
set_column_comment(table_name, column_name, options[:comment])
|
65
62
|
end
|
@@ -1,40 +1,50 @@
|
|
1
1
|
module MigrationComments::ActiveRecord::ConnectionAdapters
|
2
2
|
module SQLite3Adapter
|
3
|
-
include AbstractSQLiteAdapter
|
4
3
|
|
5
|
-
def
|
6
|
-
|
7
|
-
alias_method_chain :columns, :migration_comments
|
8
|
-
alias_method_chain :copy_table, :migration_comments
|
9
|
-
alias_method_chain :change_column, :migration_comments
|
10
|
-
end
|
4
|
+
def comments_supported?
|
5
|
+
true
|
11
6
|
end
|
12
7
|
|
13
|
-
def
|
14
|
-
|
15
|
-
|
8
|
+
def inline_comments?
|
9
|
+
true
|
10
|
+
end
|
16
11
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
}
|
12
|
+
def set_table_comment(table_name, comment_text)
|
13
|
+
alter_table(table_name, :comment => comment_text)
|
14
|
+
end
|
21
15
|
|
22
|
-
|
23
|
-
|
24
|
-
|
16
|
+
def set_column_comment(table_name, column_name, comment_text)
|
17
|
+
sql_type = primary_key(table_name) == column_name.to_s ?
|
18
|
+
:primary_key :
|
19
|
+
column_for(table_name, column_name).sql_type
|
20
|
+
change_column table_name, column_name, sql_type, :comment => comment_text
|
21
|
+
end
|
25
22
|
|
26
|
-
|
23
|
+
def retrieve_table_comment(table_name)
|
24
|
+
result = select_value(lookup_comment_sql(table_name))
|
25
|
+
$1 if result =~ /CREATE (?:TEMPORARY )?TABLE #{quote_table_name table_name} [^\(]*\/\*(.*)\*\/ \(/
|
26
|
+
end
|
27
27
|
|
28
|
-
|
29
|
-
|
28
|
+
def retrieve_column_comments(table_name, *column_names)
|
29
|
+
if column_names.empty?
|
30
|
+
return columns(table_name).inject({}) { |m, v| m[v.name.to_sym] = v.comment if v.comment.present?; m }
|
30
31
|
end
|
32
|
+
result = select_value(lookup_comment_sql(table_name))
|
33
|
+
result =~ /^CREATE (?:TEMPORARY )?TABLE "\w*" [^\(]*(?:\/\*.*\*\/ )?\((.*)\)[^\)]*$/
|
34
|
+
col_defs = $1
|
35
|
+
comment_matches = col_defs.scan(/"([^",]+)"[^,]*\/\*(.+?)\*\//)
|
36
|
+
Hash[comment_matches.map{|col_name, comment| [col_name.to_sym, comment.presence] }]
|
37
|
+
end
|
31
38
|
|
32
|
-
|
33
|
-
|
39
|
+
def create_table(table_name, options = {})
|
40
|
+
super(table_name, options) do |td|
|
41
|
+
td.comment = options[:comment] if options.has_key?(:comment)
|
42
|
+
yield td if block_given?
|
43
|
+
end
|
34
44
|
end
|
35
45
|
|
36
|
-
def
|
37
|
-
cols =
|
46
|
+
def columns(table_name)
|
47
|
+
cols = super(table_name)
|
38
48
|
comments = retrieve_column_comments(table_name, *(cols.map(&:name)))
|
39
49
|
cols.each do |col|
|
40
50
|
col.comment = comments[col.name.to_sym] if comments.has_key?(col.name.to_sym)
|
@@ -42,34 +52,51 @@ module MigrationComments::ActiveRecord::ConnectionAdapters
|
|
42
52
|
cols
|
43
53
|
end
|
44
54
|
|
45
|
-
def
|
46
|
-
from_primary_key = primary_key(from)
|
47
|
-
options[:id] = false
|
55
|
+
def copy_table(from, to, options = {}) #:nodoc:
|
48
56
|
unless options.has_key?(:comment)
|
49
57
|
table_comment = retrieve_table_comment(from)
|
50
|
-
options
|
58
|
+
options.merge!(comment: table_comment) if table_comment
|
59
|
+
end
|
60
|
+
super(from, to, options) do |definition|
|
61
|
+
retrieve_column_comments(from).each do |col_name, comment|
|
62
|
+
definition[col_name].comment = CommentDefinition.new(from, col_name, comment)
|
63
|
+
end
|
64
|
+
yield definition if block_given?
|
51
65
|
end
|
52
|
-
|
53
|
-
@definition = definition
|
54
|
-
@definition.primary_key(from_primary_key) if from_primary_key.present?
|
55
|
-
columns(from).each do |column|
|
56
|
-
column_name = options[:rename] ?
|
57
|
-
(options[:rename][column.name] ||
|
58
|
-
options[:rename][column.name.to_sym] ||
|
59
|
-
column.name) : column.name
|
60
|
-
next if column_name == from_primary_key
|
66
|
+
end
|
61
67
|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
68
|
+
def change_column(table_name, column_name, type, options = {}) #:nodoc:
|
69
|
+
super(table_name, column_name, type, options)
|
70
|
+
if options.has_key?(:comment)
|
71
|
+
alter_table(table_name) do |definition|
|
72
|
+
definition[column_name].comment = CommentDefinition.new(table_name, column_name, options[:comment])
|
66
73
|
end
|
67
|
-
yield @definition if block_given?
|
68
74
|
end
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
75
|
+
end
|
76
|
+
|
77
|
+
def comment_sql(comment_definition)
|
78
|
+
if comment_definition.nil? || comment_definition.comment_text.blank?
|
79
|
+
""
|
80
|
+
else
|
81
|
+
" /*#{escaped_comment(comment_definition.comment_text)}*/"
|
82
|
+
end
|
83
|
+
|
84
|
+
end
|
85
|
+
|
86
|
+
def add_column_options!(sql, options)
|
87
|
+
super(sql, options)
|
88
|
+
if options.keys.include?(:comment)
|
89
|
+
sql << comment_sql(CommentDefinition.new(nil, nil, options[:comment]))
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
private
|
94
|
+
def escaped_comment(comment)
|
95
|
+
comment.gsub(/\*\//, "*-/")
|
96
|
+
end
|
97
|
+
|
98
|
+
def lookup_comment_sql(table_name)
|
99
|
+
"select sql from (select * from sqlite_master where type='table' union select * from sqlite_temp_master where type='table') where tbl_name = '#{table_name}'"
|
73
100
|
end
|
74
101
|
end
|
75
102
|
end
|
@@ -1,12 +1,12 @@
|
|
1
1
|
module MigrationComments::ActiveRecord::ConnectionAdapters
|
2
2
|
module Table
|
3
3
|
def change_comment(column_name, comment_text)
|
4
|
-
@base.set_column_comment(
|
4
|
+
@base.set_column_comment(name, column_name, comment_text)
|
5
5
|
end
|
6
6
|
|
7
7
|
def change_table_comment(comment_text)
|
8
|
-
@base.set_table_comment(
|
8
|
+
@base.set_table_comment(name, comment_text)
|
9
9
|
end
|
10
|
-
|
10
|
+
alias_method :comment, :change_table_comment
|
11
11
|
end
|
12
12
|
end
|
@@ -1,33 +1,24 @@
|
|
1
1
|
module MigrationComments::ActiveRecord::ConnectionAdapters
|
2
2
|
module TableDefinition
|
3
|
+
attr_accessor :comment
|
3
4
|
|
4
|
-
|
5
|
-
|
6
|
-
base.class_eval do
|
7
|
-
alias_method_chain :column, :migration_comments
|
8
|
-
attr_accessor :base
|
9
|
-
end
|
10
|
-
end
|
11
|
-
|
12
|
-
def comment(text)
|
13
|
-
@table_comment = CommentDefinition.new(base, nil, nil, text)
|
14
|
-
self
|
5
|
+
def comment=(text)
|
6
|
+
@comment = text.respond_to?(:comment_text) ? text : CommentDefinition.new(nil, nil, text)
|
15
7
|
end
|
16
8
|
|
17
|
-
def
|
18
|
-
|
9
|
+
def column(name, type, options = {})
|
10
|
+
super(name, type, options)
|
19
11
|
if options.has_key?(:comment)
|
20
12
|
col = self[name]
|
21
|
-
col.comment = CommentDefinition.new(
|
13
|
+
col.comment = CommentDefinition.new(nil, name, options[:comment])
|
22
14
|
end
|
23
15
|
self
|
24
16
|
end
|
25
17
|
|
26
18
|
def collect_comments(table_name)
|
27
|
-
comments = []
|
28
|
-
comments
|
29
|
-
comments.
|
30
|
-
comments.each{|comment| comment.table = table_name; comment.adapter = base}
|
19
|
+
comments = [comment] + columns.map(&:comment)
|
20
|
+
comments.compact!
|
21
|
+
comments.each{|comment| comment.table_name = table_name }
|
31
22
|
end
|
32
23
|
end
|
33
24
|
end
|
@@ -1,15 +1,11 @@
|
|
1
1
|
module MigrationComments::ActiveRecord
|
2
2
|
module SchemaDumper
|
3
3
|
include MigrationComments::SchemaFormatter
|
4
|
-
def self.included(base)
|
5
|
-
base.class_eval do
|
6
|
-
alias_method_chain :table, :migration_comments
|
7
|
-
end
|
8
|
-
end
|
9
4
|
|
10
|
-
def
|
5
|
+
def table(table, stream)
|
6
|
+
return super if ::ActiveRecord::VERSION::MAJOR >= 5 && @connection.class.name !~ /SQLite/
|
11
7
|
tbl_stream = StringIO.new
|
12
|
-
|
8
|
+
super(table, tbl_stream)
|
13
9
|
tbl_stream.rewind
|
14
10
|
commented_stream = append_comments(table, tbl_stream)
|
15
11
|
tbl_stream.close
|
@@ -25,8 +21,8 @@ module MigrationComments::ActiveRecord
|
|
25
21
|
table_line = 0
|
26
22
|
col_names = {}
|
27
23
|
error = false
|
28
|
-
while (
|
29
|
-
content =
|
24
|
+
while (stream_line = stream.gets)
|
25
|
+
content = stream_line.chomp
|
30
26
|
if content =~ /^# Could not dump table "#{table_name}"/
|
31
27
|
error = true
|
32
28
|
elsif content =~ /create_table\s/
|
@@ -43,7 +39,7 @@ module MigrationComments::ActiveRecord
|
|
43
39
|
elsif table_line == index && table_comment.present?
|
44
40
|
block_init = " do |t|"
|
45
41
|
line.chomp!(block_init) << ", " << render_comment(table_comment) << block_init
|
46
|
-
elsif col_names[index]
|
42
|
+
elsif col_names[index] && ::ActiveRecord::VERSION::MAJOR < 5
|
47
43
|
comment = column_comments[col_names[index]]
|
48
44
|
line << ',' << ' ' * (len - line.length) << render_comment(comment) unless comment.blank?
|
49
45
|
end
|
@@ -1,18 +1,16 @@
|
|
1
1
|
module MigrationComments
|
2
2
|
module AnnotateModels
|
3
|
-
def self.
|
4
|
-
base
|
5
|
-
|
6
|
-
include ClassMethods
|
7
|
-
alias_method_chain :get_schema_info, :migration_comments
|
8
|
-
end
|
3
|
+
def self.prepended(base)
|
4
|
+
class << base
|
5
|
+
prepend ClassMethods
|
9
6
|
end
|
10
7
|
end
|
11
8
|
|
12
9
|
module ClassMethods
|
13
|
-
def
|
14
|
-
info = get_schema_info_without_migration_comments(*args)
|
10
|
+
def get_schema_info(*args)
|
15
11
|
klass = args[0]
|
12
|
+
klass.reset_column_information
|
13
|
+
info = super(*args)
|
16
14
|
commented_info(klass, info)
|
17
15
|
end
|
18
16
|
|
@@ -13,7 +13,14 @@ module MigrationComments
|
|
13
13
|
end
|
14
14
|
|
15
15
|
def render_value(value)
|
16
|
-
|
16
|
+
case value
|
17
|
+
when String
|
18
|
+
%Q[#{value}].inspect
|
19
|
+
when Symbol
|
20
|
+
value.inspect
|
21
|
+
else
|
22
|
+
value
|
23
|
+
end
|
17
24
|
end
|
18
25
|
end
|
19
26
|
end
|
data/migration_comments.gemspec
CHANGED
@@ -18,18 +18,11 @@ Gem::Specification.new do |s|
|
|
18
18
|
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
19
19
|
s.require_paths = ["lib"]
|
20
20
|
|
21
|
-
s.add_runtime_dependency 'activerecord', '>= 2.
|
21
|
+
s.add_runtime_dependency 'activerecord', '>= 4.2.0'
|
22
22
|
|
23
|
-
|
24
|
-
# however, the comments should work with the original 'annotate_models' plugin as well at:
|
25
|
-
# http://repo.pragprog.com/svn/Public/plugins/annotate_models
|
26
|
-
# provided the environment is not loaded until _after_ the AnnotateModels module is declared
|
27
|
-
s.add_development_dependency 'annotate', '~> 2.5.0'
|
28
|
-
|
29
|
-
# add / replace with other adapter(s) as needed
|
23
|
+
s.add_development_dependency 'annotate', '~> 2.7.0'
|
30
24
|
s.add_development_dependency 'pg'
|
31
|
-
# s.add_development_dependency 'postgres-pr'
|
32
|
-
# s.add_development_dependency 'mysql'
|
33
25
|
s.add_development_dependency 'mysql2'
|
34
26
|
s.add_development_dependency 'sqlite3'
|
27
|
+
s.add_development_dependency 'minitest-byebug'
|
35
28
|
end
|
data/test/add_comments_test.rb
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
require File.join(File.dirname(__FILE__), 'test_helper')
|
2
2
|
|
3
|
-
class AddCommentsTest < Minitest::
|
3
|
+
class AddCommentsTest < Minitest::Test
|
4
4
|
include TestHelper
|
5
5
|
|
6
6
|
def test_adding_a_table_comment
|
@@ -26,10 +26,51 @@ class AddCommentsTest < Minitest::Unit::TestCase
|
|
26
26
|
assert_nil result_field2
|
27
27
|
end
|
28
28
|
|
29
|
+
def test_adding_a_column_with_a_comment
|
30
|
+
comment_text = "a comment in a new column"
|
31
|
+
result_field1 = nil
|
32
|
+
result_field3 = nil
|
33
|
+
ActiveRecord::Schema.define do
|
34
|
+
add_column :sample, :field3, :string, :comment => comment_text
|
35
|
+
result_field3 = retrieve_column_comment :sample, :field3
|
36
|
+
result_field1 = retrieve_column_comment :sample, :field1
|
37
|
+
end
|
38
|
+
assert_equal comment_text, result_field3
|
39
|
+
assert_nil result_field1
|
40
|
+
end
|
41
|
+
|
42
|
+
def test_changing_a_column_while_adding_a_comment
|
43
|
+
comment_text = "a comment in a changing column"
|
44
|
+
result_field1 = nil
|
45
|
+
ActiveRecord::Schema.define do
|
46
|
+
change_column :sample, :field1, :string, :limit => 25, :comment => comment_text
|
47
|
+
result_field1 = retrieve_column_comment :sample, :field1
|
48
|
+
end
|
49
|
+
assert_equal comment_text, result_field1
|
50
|
+
end
|
51
|
+
|
52
|
+
def test_creating_a_temp_table_with_table_comments_and_no_block
|
53
|
+
ActiveRecord::Schema.define do
|
54
|
+
begin
|
55
|
+
create_table :sample3, temporary: true, comment: "a table comment"
|
56
|
+
ensure
|
57
|
+
drop_table :sample3 rescue nil
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
29
62
|
def test_creating_a_table_with_table_comments_and_no_block
|
63
|
+
table_comment = "a table comment"
|
64
|
+
result_table_comment = nil
|
30
65
|
ActiveRecord::Schema.define do
|
31
|
-
|
66
|
+
begin
|
67
|
+
create_table :sample3, comment: table_comment
|
68
|
+
result_table_comment = retrieve_table_comment :sample3
|
69
|
+
ensure
|
70
|
+
drop_table :sample3 rescue nil
|
71
|
+
end
|
32
72
|
end
|
73
|
+
assert_equal table_comment, result_table_comment
|
33
74
|
end
|
34
75
|
|
35
76
|
def test_creating_a_table_with_table_and_column_comments
|