deep_cloneable 1.6.1 → 1.7.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- NGNlZTg5YzA1YjhiNmFmZjI4ZDBjZTIxYmJkYTZjYjZhZjE5MWQzNA==
5
- data.tar.gz: !binary |-
6
- ZTNiYjYzMmI2YmMzOGY1NGEyNWE4ZmMzZWExNTE3NjJmYzc0ZjJkMQ==
7
- !binary "U0hBNTEy":
8
- metadata.gz: !binary |-
9
- ODQ0NDJiMzkwMzY5YzNlYmMyNjc1NTlmZTIxOWNiMDcyNjg1NWJiOGYyMGJh
10
- N2I4NDY3YWNiZmRhNjkyNTExMDMwYzBlNWZhMTEyODk0ZmM0ZGNkZDMzZmQw
11
- MDIzYjI3OTdlYmEyOWMzNWRmZTQzZjU3NTU0NDc2MjI0NTk4NGE=
12
- data.tar.gz: !binary |-
13
- YzhkMmVkYWQxYjk1MDhhMTU0MTlmNjNjNGI4NTZiNTc2M2FiZWVjOGVkNTZh
14
- NDI3NGU0YjUzMjFkNzZlNWRjMmY0ODhlZmI0MzBjZjM0M2YzNjczZjQzZWY0
15
- ZGVjNGU0OGEzYWQ1MDYxM2E1Njc5ZDU4Y2NlYzA2OTY2OWFjY2I=
2
+ SHA1:
3
+ metadata.gz: 4f8ee9b4a7a7e7e22b8a9b329e4cf95c7d5bed93
4
+ data.tar.gz: d6b6a654ee08c7c0fd903d9a75e30043033785be
5
+ SHA512:
6
+ metadata.gz: 161420b3d29dd21abd32e702f78eefed39b3dc70bad588dc94841f01c47c5e68ad71843b5d02dc70f7b5d6b893c3ee9f337cb3431e60657b4ab3919fd74d31f7
7
+ data.tar.gz: aa4d87c683367f05c1be6bc5cbf2ea725a9ec3a5a8ce5352c0f548bcb9fe7ff24303cbe07b92b41ca8eb64d2972b873748b4b99d1e77f2a96863b1096a13b89c
data/Gemfile CHANGED
@@ -1,8 +1,9 @@
1
1
  source 'http://rubygems.org'
2
2
 
3
- gem 'minitest', :group => :test
4
3
  gem 'activerecord', '>= 3.1.0'
5
- gem 'activesupport', '>= 3.1.0', :group => :test
4
+ gem 'activesupport', '>= 3.1.0'
5
+
6
+ gem 'minitest', :group => :test
6
7
  gem 'appraisal', :group => :test
7
8
  gem 'sqlite3', :group => :test
8
9
  gem 'rdoc', '>= 2.4.2', :group => :test
data/README.rdoc CHANGED
@@ -16,62 +16,66 @@ This gem gives every ActiveRecord::Base object the possibility to do a deep clon
16
16
 
17
17
  * In your Gemfile:
18
18
 
19
- gem 'deep_cloneable', '~> 1.6.1'
19
+ gem 'deep_cloneable', '~> 1.7.0'
20
+
21
+ == Note
22
+
23
+ Version 1.7.0 deprecates the use of the method 'dup' for deep cloning. Please update your code to use 'deep_clone' instead. The dup method will be removed in deep_cloneable 2.0.0.
20
24
 
21
25
  == Example
22
26
 
23
27
  === Cloning one single association
24
- pirate.dup :include => :mateys
28
+ pirate.deep_clone :include => :mateys
25
29
 
26
30
  === Cloning multiple associations
27
- pirate.dup :include => [:mateys, :treasures]
31
+ pirate.deep_clone :include => [:mateys, :treasures]
28
32
 
29
33
  === Cloning really deep
30
- pirate.dup :include => {:treasures => :gold_pieces}
34
+ pirate.deep_clone :include => {:treasures => :gold_pieces}
31
35
 
32
36
  === Cloning really deep with multiple associations
33
- pirate.dup :include => [:mateys, {:treasures => :gold_pieces}]
37
+ pirate.deep_clone :include => [:mateys, {:treasures => :gold_pieces}]
34
38
 
35
39
  === Cloning really deep with multiple associations and a dictionary
36
40
 
37
41
  A dictionary ensures that models are not cloned multiple times when it is associated to nested models.
38
42
  When using a dictionary, ensure recurring associations are cloned first:
39
43
 
40
- pirate.dup :include => [:mateys, {:treasures => [:matey, :gold_pieces]}], :use_dictionary => true
44
+ pirate.deep_clone :include => [:mateys, {:treasures => [:matey, :gold_pieces]}], :use_dictionary => true
41
45
 
42
46
  If this is not an option for you, it is also possible to populate the dictionary manually in advance:
43
47
 
44
48
  dict = { :mateys => {} }
45
- pirate.mateys.each{|m| dict[:mateys][m] = m.dup }
46
- pirate.dup :include => [:mateys, {:treasures => [:matey, :gold_pieces]}], :dictionary => dict
49
+ pirate.mateys.each{|m| dict[:mateys][m] = m.deep_clone }
50
+ pirate.deep_clone :include => [:mateys, {:treasures => [:matey, :gold_pieces]}], :dictionary => dict
47
51
 
48
- When an object isn't found in the dictionary, it will be populated. By passing in an empty dictionary you can populate it automatically and reuse it in subsequent dups to avoid creating multiples of the same object where you have overlapping associations.
52
+ When an object isn't found in the dictionary, it will be populated. By passing in an empty dictionary you can populate it automatically and reuse it in subsequent deep_clones to avoid creating multiples of the same object where you have overlapping associations.
49
53
 
50
54
  === Cloning a model without an attribute
51
- pirate.dup :except => :name
55
+ pirate.deep_clone :except => :name
52
56
 
53
57
  === Cloning a model without multiple attributes
54
- pirate.dup :except => [:name, :nick_name]
58
+ pirate.deep_clone :except => [:name, :nick_name]
55
59
 
56
60
  === Cloning a model without an attribute or nested multiple attributes
57
- pirate.dup :include => :parrot, :except => [:name, { :parrot => [:name] }]
61
+ pirate.deep_clone :include => :parrot, :except => [:name, { :parrot => [:name] }]
58
62
 
59
63
  === Cloning with a block
60
- pirate.dup :include => :parrot do |original, kopy|
64
+ pirate.deep_clone :include => :parrot do |original, kopy|
61
65
  kopy.cloned_from_id = original.id if kopy.respond_to?(:cloned_from_id)
62
66
  end
63
67
 
64
68
  === Cloning without validations
65
- pirate.dup :include => {:treasures => :gold_pieces}, :validate => false
69
+ pirate.deep_clone :include => {:treasures => :gold_pieces}, :validate => false
66
70
 
67
71
  === Cloning a model with only explicitly assigned attribute
68
- pirate.dup :only => :name
72
+ pirate.deep_clone :only => :name
69
73
 
70
74
  === Cloning a model with only multiple explicitly assigned attributes
71
- pirate.dup :only => [:name, :nick_name]
75
+ pirate.deep_clone :only => [:name, :nick_name]
72
76
 
73
77
  === Cloning a model with explicitly assigned attributes or nested multiple attributes
74
- pirate.dup :include => :parrot, :only => [:name, { :parrot => [:name] }]
78
+ pirate.deep_clone :include => :parrot, :only => [:name, { :parrot => [:name] }]
75
79
 
76
80
  == Note on Patches/Pull Requests
77
81
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.6.1
1
+ 1.7.0
@@ -2,14 +2,16 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
+ # stub: deep_cloneable 1.7.0 ruby lib
5
6
 
6
7
  Gem::Specification.new do |s|
7
8
  s.name = "deep_cloneable"
8
- s.version = "1.6.1"
9
+ s.version = "1.7.0"
9
10
 
10
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
12
+ s.require_paths = ["lib"]
11
13
  s.authors = ["Reinier de Lange"]
12
- s.date = "2014-04-18"
14
+ s.date = "2014-06-25"
13
15
  s.description = "Extends the functionality of ActiveRecord::Base#clone to perform a deep clone that includes user specified associations. "
14
16
  s.email = "r.j.delange@nedforce.nl"
15
17
  s.extra_rdoc_files = [
@@ -44,8 +46,7 @@ Gem::Specification.new do |s|
44
46
  "test/test_helper.rb"
45
47
  ]
46
48
  s.homepage = "http://github.com/moiristo/deep_cloneable"
47
- s.require_paths = ["lib"]
48
- s.rubygems_version = "2.0.6"
49
+ s.rubygems_version = "2.2.2"
49
50
  s.summary = "This gem gives every ActiveRecord::Base object the possibility to do a deep clone."
50
51
 
51
52
  if s.respond_to? :specification_version then
@@ -53,11 +54,14 @@ Gem::Specification.new do |s|
53
54
 
54
55
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
55
56
  s.add_runtime_dependency(%q<activerecord>, [">= 3.1.0"])
57
+ s.add_runtime_dependency(%q<activesupport>, [">= 3.1.0"])
56
58
  else
57
59
  s.add_dependency(%q<activerecord>, [">= 3.1.0"])
60
+ s.add_dependency(%q<activesupport>, [">= 3.1.0"])
58
61
  end
59
62
  else
60
63
  s.add_dependency(%q<activerecord>, [">= 3.1.0"])
64
+ s.add_dependency(%q<activesupport>, [">= 3.1.0"])
61
65
  end
62
66
  end
63
67
 
@@ -17,18 +17,18 @@ class ActiveRecord::Base
17
17
  end
18
18
 
19
19
  # Deep dups an ActiveRecord model. See README.rdoc
20
- def dup *args, &block
20
+ def deep_clone *args, &block
21
21
  options = args[0] || {}
22
22
 
23
23
  dict = options[:dictionary]
24
24
  dict ||= {} if options.delete(:use_dictionary)
25
25
 
26
26
  kopy = unless dict
27
- super()
27
+ dup()
28
28
  else
29
29
  tableized_class = self.class.name.tableize.to_sym
30
30
  dict[tableized_class] ||= {}
31
- dict[tableized_class][self] ||= super()
31
+ dict[tableized_class][self] ||= dup()
32
32
  end
33
33
 
34
34
  block.call(self, kopy) if block
@@ -91,10 +91,16 @@ class ActiveRecord::Base
91
91
  return kopy
92
92
  end
93
93
 
94
+ def dup *args, &block
95
+ return super() if args.empty? && !block
96
+ ActiveSupport::Deprecation.warn("Calling dup with arguments or blocks is deprecated and will be removed in deep_cloneable 2. Use method 'deep_clone' instead.")
97
+ deep_clone *args, &block
98
+ end
99
+
94
100
  private
95
101
 
96
102
  def dup_belongs_to_association options, &block
97
- self.send(options[:association]) && self.send(options[:association]).dup(options[:dup_options], &block)
103
+ self.send(options[:association]) && self.send(options[:association]).deep_clone(options[:dup_options], &block)
98
104
  end
99
105
 
100
106
  def dup_has_one_association options, &block
@@ -109,7 +115,7 @@ class ActiveRecord::Base
109
115
  end.try(:name)
110
116
 
111
117
  self.send(options[:association]).collect do |obj|
112
- tmp = obj.dup(options[:dup_options], &block)
118
+ tmp = obj.deep_clone(options[:dup_options], &block)
113
119
  tmp.send("#{primary_key_name}=", nil)
114
120
  tmp.send("#{reverse_association_name.to_s}=", options[:copy]) if reverse_association_name
115
121
  tmp
@@ -11,155 +11,155 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
11
11
  @ship = BattleShip.create(:name => 'Black Pearl', :pirates => [@jack])
12
12
  end
13
13
 
14
- def test_single_dup_exception
15
- dup = @jack.dup(:except => :name)
16
- assert dup.new_record?
17
- assert dup.save
18
- assert_equal @jack.name, @jack.dup.name
19
- assert_nil dup.name
20
- assert_equal @jack.nick_name, dup.nick_name
21
- end
22
-
23
- def test_multiple_dup_exception
24
- dup = @jack.dup(:except => [:name, :nick_name])
25
- assert dup.new_record?
26
- assert dup.save
27
- assert_nil dup.name
28
- assert_equal 'no nickname', dup.nick_name
29
- assert_equal @jack.age, dup.age
30
- end
31
-
32
- def test_single_dup_onliness
33
- dup = @jack.dup(:only => :name)
34
- assert dup.new_record?
35
- assert dup.save
36
- assert_equal @jack.name, dup.name
37
- assert_equal 'no nickname', dup.nick_name
38
- assert_nil dup.age
39
- assert_nil dup.ship_id
40
- assert_nil dup.ship_type
41
- end
42
-
43
- def test_multiple_dup_onliness
44
- dup = @jack.dup(:only => [:name, :nick_name])
45
- assert dup.new_record?
46
- assert dup.save
47
- assert_equal @jack.name, dup.name
48
- assert_equal @jack.nick_name, dup.nick_name
49
- assert_nil dup.age
50
- assert_nil dup.ship_id
51
- assert_nil dup.ship_type
14
+ def test_single_deep_clone_exception
15
+ deep_clone = @jack.deep_clone(:except => :name)
16
+ assert deep_clone.new_record?
17
+ assert deep_clone.save
18
+ assert_equal @jack.name, @jack.deep_clone.name
19
+ assert_nil deep_clone.name
20
+ assert_equal @jack.nick_name, deep_clone.nick_name
21
+ end
22
+
23
+ def test_multiple_deep_clone_exception
24
+ deep_clone = @jack.deep_clone(:except => [:name, :nick_name])
25
+ assert deep_clone.new_record?
26
+ assert deep_clone.save
27
+ assert_nil deep_clone.name
28
+ assert_equal 'no nickname', deep_clone.nick_name
29
+ assert_equal @jack.age, deep_clone.age
30
+ end
31
+
32
+ def test_single_deep_clone_onliness
33
+ deep_clone = @jack.deep_clone(:only => :name)
34
+ assert deep_clone.new_record?
35
+ assert deep_clone.save
36
+ assert_equal @jack.name, deep_clone.name
37
+ assert_equal 'no nickname', deep_clone.nick_name
38
+ assert_nil deep_clone.age
39
+ assert_nil deep_clone.ship_id
40
+ assert_nil deep_clone.ship_type
41
+ end
42
+
43
+ def test_multiple_deep_clone_onliness
44
+ deep_clone = @jack.deep_clone(:only => [:name, :nick_name])
45
+ assert deep_clone.new_record?
46
+ assert deep_clone.save
47
+ assert_equal @jack.name, deep_clone.name
48
+ assert_equal @jack.nick_name, deep_clone.nick_name
49
+ assert_nil deep_clone.age
50
+ assert_nil deep_clone.ship_id
51
+ assert_nil deep_clone.ship_type
52
52
  end
53
53
 
54
54
  def test_single_include_association
55
- dup = @jack.dup(:include => :mateys)
56
- assert dup.new_record?
57
- assert dup.save
58
- assert_equal 1, dup.mateys.size
55
+ deep_clone = @jack.deep_clone(:include => :mateys)
56
+ assert deep_clone.new_record?
57
+ assert deep_clone.save
58
+ assert_equal 1, deep_clone.mateys.size
59
59
  end
60
60
 
61
61
  def test_single_include_belongs_to_polymorphic_association
62
- dup = @jack.dup(:include => :ship)
63
- assert dup.new_record?
64
- assert dup.save
65
- refute_nil dup.ship
66
- refute_equal @jack.ship, dup.ship
62
+ deep_clone = @jack.deep_clone(:include => :ship)
63
+ assert deep_clone.new_record?
64
+ assert deep_clone.save
65
+ refute_nil deep_clone.ship
66
+ refute_equal @jack.ship, deep_clone.ship
67
67
  end
68
68
 
69
69
  def test_single_include_has_many_polymorphic_association
70
- dup = @ship.dup(:include => :pirates)
71
- assert dup.new_record?
72
- assert dup.save
73
- assert dup.pirates.any?
70
+ deep_clone = @ship.deep_clone(:include => :pirates)
71
+ assert deep_clone.new_record?
72
+ assert deep_clone.save
73
+ assert deep_clone.pirates.any?
74
74
  end
75
75
 
76
76
  def test_multiple_include_association
77
- dup = @jack.dup(:include => [:mateys, :treasures])
78
- assert dup.new_record?
79
- assert dup.save
80
- assert_equal 1, dup.mateys.size
81
- assert_equal 1, dup.treasures.size
77
+ deep_clone = @jack.deep_clone(:include => [:mateys, :treasures])
78
+ assert deep_clone.new_record?
79
+ assert deep_clone.save
80
+ assert_equal 1, deep_clone.mateys.size
81
+ assert_equal 1, deep_clone.treasures.size
82
82
  end
83
83
 
84
84
  def test_deep_include_association
85
- dup = @jack.dup(:include => {:treasures => :gold_pieces})
86
- assert dup.new_record?
87
- assert dup.save
88
- assert_equal 1, dup.treasures.size
89
- assert_equal 1, dup.gold_pieces.size
85
+ deep_clone = @jack.deep_clone(:include => {:treasures => :gold_pieces})
86
+ assert deep_clone.new_record?
87
+ assert deep_clone.save
88
+ assert_equal 1, deep_clone.treasures.size
89
+ assert_equal 1, deep_clone.gold_pieces.size
90
90
  end
91
91
 
92
92
  def test_include_association_assignments
93
- dup = @jack.dup(:include => :treasures)
94
- assert dup.new_record?
93
+ deep_clone = @jack.deep_clone(:include => :treasures)
94
+ assert deep_clone.new_record?
95
95
 
96
- dup.treasures.each do |treasure|
97
- assert_equal dup, treasure.pirate
96
+ deep_clone.treasures.each do |treasure|
97
+ assert_equal deep_clone, treasure.pirate
98
98
  end
99
99
  end
100
100
 
101
101
  def test_multiple_and_deep_include_association
102
- dup = @jack.dup(:include => {:treasures => :gold_pieces, :mateys => {}})
103
- assert dup.new_record?
104
- assert dup.save
105
- assert_equal 1, dup.treasures.size
106
- assert_equal 1, dup.gold_pieces.size
107
- assert_equal 1, dup.mateys.size
102
+ deep_clone = @jack.deep_clone(:include => {:treasures => :gold_pieces, :mateys => {}})
103
+ assert deep_clone.new_record?
104
+ assert deep_clone.save
105
+ assert_equal 1, deep_clone.treasures.size
106
+ assert_equal 1, deep_clone.gold_pieces.size
107
+ assert_equal 1, deep_clone.mateys.size
108
108
  end
109
109
 
110
110
  def test_multiple_and_deep_include_association_with_array
111
- dup = @jack.dup(:include => [{:treasures => :gold_pieces}, :mateys])
112
- assert dup.new_record?
113
- assert dup.save
114
- assert_equal 1, dup.treasures.size
115
- assert_equal 1, dup.gold_pieces.size
116
- assert_equal 1, dup.mateys.size
111
+ deep_clone = @jack.deep_clone(:include => [{:treasures => :gold_pieces}, :mateys])
112
+ assert deep_clone.new_record?
113
+ assert deep_clone.save
114
+ assert_equal 1, deep_clone.treasures.size
115
+ assert_equal 1, deep_clone.gold_pieces.size
116
+ assert_equal 1, deep_clone.mateys.size
117
117
  end
118
118
 
119
119
  def test_with_belongs_to_relation
120
- dup = @jack.dup(:include => :parrot)
121
- assert dup.new_record?
122
- assert dup.save
123
- refute_equal dup.parrot, @jack.parrot
120
+ deep_clone = @jack.deep_clone(:include => :parrot)
121
+ assert deep_clone.new_record?
122
+ assert deep_clone.save
123
+ refute_equal deep_clone.parrot, @jack.parrot
124
124
  end
125
125
 
126
126
  def test_should_pass_nested_exceptions
127
- dup = @jack.dup(:include => :parrot, :except => [:name, { :parrot => [:name] }])
128
- assert dup.new_record?
129
- assert dup.save
130
- refute_equal dup.parrot, @jack.parrot
131
- assert_equal dup.parrot.age, @jack.parrot.age
127
+ deep_clone = @jack.deep_clone(:include => :parrot, :except => [:name, { :parrot => [:name] }])
128
+ assert deep_clone.new_record?
129
+ assert deep_clone.save
130
+ refute_equal deep_clone.parrot, @jack.parrot
131
+ assert_equal deep_clone.parrot.age, @jack.parrot.age
132
132
  refute_nil @jack.parrot.name
133
- assert_nil dup.parrot.name
133
+ assert_nil deep_clone.parrot.name
134
134
  end
135
135
 
136
136
  def test_should_pass_nested_onlinesses
137
- dup = @jack.dup(:include => :parrot, :only => [:name, { :parrot => [:name] }])
138
- assert dup.new_record?
139
- assert dup.save
140
- refute_equal dup.parrot, @jack.parrot
141
- assert_equal dup.parrot.name, @jack.parrot.name
142
- assert_nil dup.parrot.age
137
+ deep_clone = @jack.deep_clone(:include => :parrot, :only => [:name, { :parrot => [:name] }])
138
+ assert deep_clone.new_record?
139
+ assert deep_clone.save
140
+ refute_equal deep_clone.parrot, @jack.parrot
141
+ assert_equal deep_clone.parrot.name, @jack.parrot.name
142
+ assert_nil deep_clone.parrot.age
143
143
  end
144
144
 
145
- def test_should_not_double_dup_when_using_dictionary
145
+ def test_should_not_double_deep_clone_when_using_dictionary
146
146
  current_matey_count = Matey.count
147
- dup = @jack.dup(:include => [:mateys, { :treasures => :matey }], :use_dictionary => true)
148
- assert dup.new_record?
149
- dup.save!
147
+ deep_clone = @jack.deep_clone(:include => [:mateys, { :treasures => :matey }], :use_dictionary => true)
148
+ assert deep_clone.new_record?
149
+ deep_clone.save!
150
150
 
151
151
  assert_equal current_matey_count + 1, Matey.count
152
152
  end
153
153
 
154
- def test_should_not_double_dup_when_using_manual_dictionary
154
+ def test_should_not_double_deep_clone_when_using_manual_dictionary
155
155
  current_matey_count = Matey.count
156
156
 
157
157
  dict = { :mateys => {} }
158
- @jack.mateys.each{|m| dict[:mateys][m] = m.dup }
158
+ @jack.mateys.each{|m| dict[:mateys][m] = m.deep_clone }
159
159
 
160
- dup = @jack.dup(:include => [:mateys, { :treasures => :matey }], :dictionary => dict)
161
- assert dup.new_record?
162
- dup.save!
160
+ deep_clone = @jack.deep_clone(:include => [:mateys, { :treasures => :matey }], :dictionary => dict)
161
+ assert deep_clone.new_record?
162
+ deep_clone.save!
163
163
 
164
164
  assert_equal current_matey_count + 1, Matey.count
165
165
  end
@@ -168,21 +168,21 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
168
168
  @human = Animal::Human.create :name => "Michael"
169
169
  @pig = Animal::Pig.create :human => @human, :name => 'big pig'
170
170
 
171
- dup_human = @human.dup(:include => [:pigs])
172
- assert dup_human.new_record?
173
- assert dup_human.save
174
- assert_equal 1, dup_human.pigs.count
171
+ deep_clone_human = @human.deep_clone(:include => [:pigs])
172
+ assert deep_clone_human.new_record?
173
+ assert deep_clone_human.save
174
+ assert_equal 1, deep_clone_human.pigs.count
175
175
 
176
176
  @human2 = Animal::Human.create :name => "John"
177
177
  @pig2 = @human2.pigs.create :name => 'small pig'
178
178
 
179
- dup_human_2 = @human.dup(:include => [:pigs])
180
- assert dup_human_2.new_record?
181
- assert dup_human_2.save
182
- assert_equal 1, dup_human_2.pigs.count
179
+ deep_clone_human_2 = @human.deep_clone(:include => [:pigs])
180
+ assert deep_clone_human_2.new_record?
181
+ assert deep_clone_human_2.save
182
+ assert_equal 1, deep_clone_human_2.pigs.count
183
183
  end
184
184
 
185
- def test_should_dup_many_to_many_associations
185
+ def test_should_deep_clone_many_to_many_associations
186
186
  @human = Animal::Human.create :name => "Michael"
187
187
  @human2 = Animal::Human.create :name => "Jack"
188
188
  @chicken1 = Animal::Chicken.create :name => 'Chick1'
@@ -190,24 +190,24 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
190
190
  @human.chickens << [@chicken1, @chicken2]
191
191
  @human2.chickens << [@chicken1, @chicken2]
192
192
 
193
- dup_human = @human.dup(:include => :ownerships)
194
- assert dup_human.new_record?
195
- assert dup_human.save
196
- assert_equal 2, dup_human.chickens.count
193
+ deep_clone_human = @human.deep_clone(:include => :ownerships)
194
+ assert deep_clone_human.new_record?
195
+ assert deep_clone_human.save
196
+ assert_equal 2, deep_clone_human.chickens.count
197
197
  end
198
198
 
199
- def test_should_dup_with_block
200
- dup = @jack.dup(:include => :parrot) do |original, kopy|
199
+ def test_should_deep_clone_with_block
200
+ deep_clone = @jack.deep_clone(:include => :parrot) do |original, kopy|
201
201
  kopy.cloned_from_id = original.id
202
202
  end
203
203
 
204
- assert dup.new_record?
205
- assert dup.save
206
- assert_equal @jack.id, dup.cloned_from_id
207
- assert_equal @jack.parrot.id, dup.parrot.cloned_from_id
204
+ assert deep_clone.new_record?
205
+ assert deep_clone.save
206
+ assert_equal @jack.id, deep_clone.cloned_from_id
207
+ assert_equal @jack.parrot.id, deep_clone.parrot.cloned_from_id
208
208
  end
209
209
 
210
- def test_should_dup_habtm_associations
210
+ def test_should_deep_clone_habtm_associations
211
211
  @person1 = Person.create :name => "Bill"
212
212
  @person2 = Person.create :name => "Ted"
213
213
  @car1 = Car.create :name => 'Mustang'
@@ -215,42 +215,42 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
215
215
  @person1.cars << [@car1, @car2]
216
216
  @person2.cars << [@car1, @car2]
217
217
 
218
- dup_person = @person1.dup :include => :cars
218
+ deep_clone_person = @person1.deep_clone :include => :cars
219
219
 
220
- assert dup_person.new_record?
221
- assert_equal [@person1, @person2, dup_person], @car1.people
222
- assert_equal [@person1, @person2, dup_person], @car2.people
220
+ assert deep_clone_person.new_record?
221
+ assert_equal [@person1, @person2, deep_clone_person], @car1.people
222
+ assert_equal [@person1, @person2, deep_clone_person], @car2.people
223
223
 
224
- assert dup_person.save
224
+ assert deep_clone_person.save
225
225
 
226
- # did NOT dup the Car instances
226
+ # did NOT deep_clone the Car instances
227
227
  assert_equal 2, Car.all.count
228
228
 
229
- # did dup the correct join table rows
230
- assert_equal @person1.cars, dup_person.cars
231
- assert_equal 2, dup_person.cars.count
229
+ # did deep_clone the correct join table rows
230
+ assert_equal @person1.cars, deep_clone_person.cars
231
+ assert_equal 2, deep_clone_person.cars.count
232
232
  end
233
233
 
234
- def test_should_dup_habtm_associations_with_missing_reverse_association
234
+ def test_should_deep_clone_habtm_associations_with_missing_reverse_association
235
235
  @coin = Coin.create :value => 1
236
236
  @person = Person.create :name => "Bill"
237
237
  @coin.people << @person
238
238
 
239
- dup = @coin.dup :include => :people
240
- assert dup.new_record?
239
+ deep_clone = @coin.deep_clone :include => :people
240
+ assert deep_clone.new_record?
241
241
  assert_equal [@person], @coin.people
242
- assert dup.save
242
+ assert deep_clone.save
243
243
  end
244
244
 
245
- def test_should_dup_joined_association
245
+ def test_should_deep_clone_joined_association
246
246
  subject1 = Subject.create(:name => 'subject 1')
247
247
  subject2 = Subject.create(:name => 'subject 2')
248
248
  student = Student.create(:name => 'Parent', :subjects => [subject1, subject2])
249
249
 
250
- dup = student.dup :include => { :student_assignments => :subject }
251
- dup.save # Subjects will have been set after save
252
- assert_equal 2, dup.subjects.size
253
- [subject1, subject2].each{|subject| assert !dup.subjects.include?(subject) }
250
+ deep_clone = student.deep_clone :include => { :student_assignments => :subject }
251
+ deep_clone.save # Subjects will have been set after save
252
+ assert_equal 2, deep_clone.subjects.size
253
+ [subject1, subject2].each{|subject| assert !deep_clone.subjects.include?(subject) }
254
254
  end
255
255
 
256
256
  def test_parent_validations_run_on_save_after_clone
@@ -258,13 +258,13 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
258
258
  parent = ParentWithValidation.new :children => [child]
259
259
  parent.save :validate => false
260
260
 
261
- dup_parent = parent.dup :include => :children
261
+ deep_clone_parent = parent.deep_clone :include => :children
262
262
 
263
- assert !dup_parent.save
264
- assert dup_parent.new_record?
265
- assert !dup_parent.valid?
266
- assert dup_parent.children.first.valid?
267
- assert_equal dup_parent.errors.messages, :name => ["can't be blank"]
263
+ assert !deep_clone_parent.save
264
+ assert deep_clone_parent.new_record?
265
+ assert !deep_clone_parent.valid?
266
+ assert deep_clone_parent.children.first.valid?
267
+ assert_equal deep_clone_parent.errors.messages, :name => ["can't be blank"]
268
268
  end
269
269
 
270
270
  def test_parent_validations_dont_run_on_save_after_clone
@@ -272,13 +272,13 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
272
272
  parent = ParentWithValidation.new :children => [child]
273
273
  parent.save :validate => false
274
274
 
275
- dup_parent = parent.dup :include => :children, :validate => false
275
+ deep_clone_parent = parent.deep_clone :include => :children, :validate => false
276
276
 
277
- assert dup_parent.save
278
- assert !dup_parent.new_record?
279
- assert !dup_parent.valid?
280
- assert dup_parent.children.first.valid?
281
- assert_equal dup_parent.errors.messages, :name => ["can't be blank"]
277
+ assert deep_clone_parent.save
278
+ assert !deep_clone_parent.new_record?
279
+ assert !deep_clone_parent.valid?
280
+ assert deep_clone_parent.children.first.valid?
281
+ assert_equal deep_clone_parent.errors.messages, :name => ["can't be blank"]
282
282
  end
283
283
 
284
284
  def test_child_validations_run_on_save_after_clone
@@ -286,13 +286,13 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
286
286
  child.save :validate => false
287
287
  parent = ParentWithValidation.create :name => 'John', :children => [child]
288
288
 
289
- dup_parent = parent.dup :include => :children
289
+ deep_clone_parent = parent.deep_clone :include => :children
290
290
 
291
- assert !dup_parent.save
292
- assert dup_parent.new_record?
293
- assert !dup_parent.valid?
294
- assert !dup_parent.children.first.valid?
295
- assert_equal dup_parent.errors.messages, :children => ["is invalid"]
291
+ assert !deep_clone_parent.save
292
+ assert deep_clone_parent.new_record?
293
+ assert !deep_clone_parent.valid?
294
+ assert !deep_clone_parent.children.first.valid?
295
+ assert_equal deep_clone_parent.errors.messages, :children => ["is invalid"]
296
296
  end
297
297
 
298
298
  def test_child_validations_run_on_save_after_clone
@@ -300,13 +300,13 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
300
300
  child.save :validate => false
301
301
  parent = ParentWithValidation.create :name => 'John', :children => [child]
302
302
 
303
- dup_parent = parent.dup :include => :children, :validate => false
303
+ deep_clone_parent = parent.deep_clone :include => :children, :validate => false
304
304
 
305
- assert dup_parent.save
306
- assert !dup_parent.new_record?
307
- assert !dup_parent.valid?
308
- assert !dup_parent.children.first.valid?
309
- assert_equal dup_parent.errors.messages, :children => ["is invalid"]
305
+ assert deep_clone_parent.save
306
+ assert !deep_clone_parent.new_record?
307
+ assert !deep_clone_parent.valid?
308
+ assert !deep_clone_parent.children.first.valid?
309
+ assert_equal deep_clone_parent.errors.messages, :children => ["is invalid"]
310
310
  end
311
311
 
312
312
  def test_self_join_has_many
@@ -314,9 +314,9 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
314
314
  child1 = Part.create(:name => 'Child 1', :parent_part_id => parent_part.id)
315
315
  child2 = Part.create(:name => 'Child 2', :parent_part_id => parent_part.id)
316
316
 
317
- dup_part = parent_part.dup :include => :child_parts
318
- assert dup_part.save
319
- assert_equal 2, dup_part.child_parts.size
317
+ deep_clone_part = parent_part.deep_clone :include => :child_parts
318
+ assert deep_clone_part.save
319
+ assert_equal 2, deep_clone_part.child_parts.size
320
320
  end
321
321
 
322
322
  def test_should_include_has_many_through_associations
@@ -324,9 +324,30 @@ class TestDeepCloneable < MiniTest::Unit::TestCase
324
324
  subject2 = Subject.create(:name => 'subject 2')
325
325
  student = Student.create(:name => 'Parent', :subjects => [subject1, subject2])
326
326
 
327
- dup = student.dup :include => :subjects
328
- assert_equal 2, dup.subjects.size
329
- assert_equal [[student, dup],[student, dup]], dup.subjects.map{|subject| subject.students }
327
+ deep_clone = student.deep_clone :include => :subjects
328
+ assert_equal 2, deep_clone.subjects.size
329
+ assert_equal [[student, deep_clone],[student, deep_clone]], deep_clone.subjects.map{|subject| subject.students }
330
+ end
331
+
332
+ def test_should_deep_clone_unsaved_objects
333
+ jack = Pirate.new(:name => 'Jack Sparrow', :nick_name => 'Captain Jack', :age => 30)
334
+ jack.mateys.build(:name => 'John')
335
+
336
+ deep_clone = jack.deep_clone(:include => :mateys)
337
+ assert deep_clone.new_record?
338
+ assert_equal 1, deep_clone.mateys.size
339
+ assert_equal 'John', deep_clone.mateys.first.name
340
+ end
341
+
342
+ def test_should_deep_clone_via_dup
343
+ deep_clone = @jack.dup(:include => :parrot) do |original, kopy|
344
+ kopy.cloned_from_id = original.id
345
+ end
346
+
347
+ assert deep_clone.new_record?
348
+ assert deep_clone.save
349
+ assert_equal @jack.id, deep_clone.cloned_from_id
350
+ assert_equal @jack.parrot.id, deep_clone.parrot.cloned_from_id
330
351
  end
331
352
 
332
353
  end
metadata CHANGED
@@ -1,31 +1,45 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: deep_cloneable
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.6.1
4
+ version: 1.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Reinier de Lange
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-04-18 00:00:00.000000000 Z
11
+ date: 2014-06-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
+ name: activerecord
14
15
  requirement: !ruby/object:Gem::Requirement
15
16
  requirements:
16
- - - ! '>='
17
+ - - ">="
17
18
  - !ruby/object:Gem::Version
18
19
  version: 3.1.0
20
+ type: :runtime
21
+ prerelease: false
19
22
  version_requirements: !ruby/object:Gem::Requirement
20
23
  requirements:
21
- - - ! '>='
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: 3.1.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: activesupport
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
22
32
  - !ruby/object:Gem::Version
23
33
  version: 3.1.0
24
34
  type: :runtime
25
35
  prerelease: false
26
- name: activerecord
27
- description: ! 'Extends the functionality of ActiveRecord::Base#clone to perform a
28
- deep clone that includes user specified associations. '
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: 3.1.0
41
+ description: 'Extends the functionality of ActiveRecord::Base#clone to perform a deep
42
+ clone that includes user specified associations. '
29
43
  email: r.j.delange@nedforce.nl
30
44
  executables: []
31
45
  extensions: []
@@ -33,8 +47,8 @@ extra_rdoc_files:
33
47
  - LICENSE
34
48
  - README.rdoc
35
49
  files:
36
- - .document
37
- - .travis.yml
50
+ - ".document"
51
+ - ".travis.yml"
38
52
  - Appraisals
39
53
  - Gemfile
40
54
  - Gemfile.lock
@@ -67,17 +81,17 @@ require_paths:
67
81
  - lib
68
82
  required_ruby_version: !ruby/object:Gem::Requirement
69
83
  requirements:
70
- - - ! '>='
84
+ - - ">="
71
85
  - !ruby/object:Gem::Version
72
86
  version: '0'
73
87
  required_rubygems_version: !ruby/object:Gem::Requirement
74
88
  requirements:
75
- - - ! '>='
89
+ - - ">="
76
90
  - !ruby/object:Gem::Version
77
91
  version: '0'
78
92
  requirements: []
79
93
  rubyforge_project:
80
- rubygems_version: 2.0.6
94
+ rubygems_version: 2.2.2
81
95
  signing_key:
82
96
  specification_version: 4
83
97
  summary: This gem gives every ActiveRecord::Base object the possibility to do a deep