dirty_hashy 0.1.1 → 0.1.2

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/CHANGELOG.rdoc CHANGED
@@ -1,5 +1,11 @@
1
1
  = DirtyHashy CHANGELOG
2
2
 
3
+ == Version 0.1.2 (December 24, 2011)
4
+
5
+ * Moved restricted keys logic from MethodMap to DirtyHash and thus being able to restrict keys of a DirtyHashy without dirty mapping ^^
6
+ * Corrected DirtyHashy.replace and DirtyHashy.clear in order to dirty track involved changes
7
+ * Improved :attributes= implementation within DirtyAttributes
8
+
3
9
  == Version 0.1.1 (December 24, 2011)
4
10
 
5
11
  * Added convenience methods (with MethodMap) like +name+, +name=+, +name_changed?+, +name_was+ and +name_change+
data/Gemfile CHANGED
@@ -13,4 +13,5 @@ end
13
13
  group :gem_test do
14
14
  gem "minitest"
15
15
  gem "mocha"
16
+ gem "pry"
16
17
  end
data/README.textile CHANGED
@@ -4,7 +4,7 @@ Dirty tracking within hashes with indifferent access or objects as it is expecte
4
4
 
5
5
  h2. Introduction
6
6
 
7
- "Dirty tracking / objects":http://ryandaigle.com/articles/2008/3/31/what-s-new-in-edge-rails-dirty-objects is a common programming concept. In short, it is the mechanism to track whether or not the attributes of an object have been changed and if so, which ones.
7
+ "Dirty tracking / objects":http://ryandaigle.com/articles/2008/3/31/what-s-new-in-edge-rails-dirty-objects is a common programming concept. In short, it is the concept of tracking whether or not the attributes of an object have been changed and if so, which ones.
8
8
 
9
9
  It is mostly implemented within ORM's, a couple of examples in the Ruby world are "ActiveRecord":http://ar.rubyonrails.org/classes/ActiveRecord/Dirty.html, "DataMapper":http://rubydoc.info/gems/dm-core/1.1.0/file/README.rdoc, "Mongoid":http://mongoid.org/docs/documents/dirty.html and "CouchRest Model":http://www.couchrest.info/model/dirty_tracking.html.
10
10
 
@@ -88,8 +88,35 @@ You can map methods within a DirtyHashy in order to provide convenience methods
88
88
  h.name = "Engel"
89
89
  h.name_was #=> "Paul"
90
90
  h.name_change #=> ["Paul", "Engel"]
91
- h.foo = "Bar"
92
- h.changes #=> {"name"=>["Paul", "Engel"], "foo"=>[nil, "Bar"]}
91
+ h.foo = "bar"
92
+ h.changes #=> {"name"=>["Paul", "Engel"], "foo"=>[nil, "bar"]}
93
+ </pre>
94
+
95
+ h3. Method mapping DirtyHashy with key restriction
96
+
97
+ Along with providing convenience methods, you can also restrict the range of keys you are permitted to read / write / merge / replace of a DirtyHash:
98
+
99
+ <pre>
100
+ require "rubygems"
101
+ require "dirty_hashy"
102
+
103
+ h = DirtyHashy.new({}, true, [:name])
104
+ h.dirty? #=> false
105
+ h.name #=> nil
106
+ h.name = "Paul"
107
+ h.dirty? #=> true
108
+ h.name_changed? #=> true
109
+ h.name_was #=> nil
110
+ h.name_change #=> [nil, "Paul"]
111
+ h.merge! :name => "Engel"
112
+ h.name #=> "Engel"
113
+ h.name_was #=> nil
114
+ h.name_change #=> [nil, "Engel"]
115
+ h.foo #=> NoMethodError: undefined method `foo' for {"name"=>"Engel"}:DirtyHashy
116
+ h.foo = "bar" #=> NoMethodError: undefined method `foo=' for {"name"=>"Engel"}:DirtyHashy
117
+ h.clean_up!
118
+ h.replace :name => "Paul"
119
+ h.changes #=> {"name"=>["Engel", "Paul"]}
93
120
  </pre>
94
121
 
95
122
  h3. Dirty tracking objects (models)
@@ -159,6 +186,7 @@ You can use @Person@ objects as you would expect:
159
186
  p.clean_up!
160
187
  p.dirty? #=> false
161
188
  p.name #=> "Paul"
189
+ p.foo = "bar" #=> NoMethodError: undefined method `foo=' for #<Person:0x00000100d89860>
162
190
  </pre>
163
191
 
164
192
  And last but not least: don't care about specifying the attributes available? Well don't! ;)
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.1
1
+ 0.1.2
data/dirty_hashy.gemspec CHANGED
@@ -12,7 +12,7 @@ Gem::Specification.new do |gem|
12
12
  gem.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
13
13
  gem.name = "dirty_hashy"
14
14
  gem.require_paths = ["lib"]
15
- gem.version = "0.1.1"
15
+ gem.version = "0.1.2"
16
16
 
17
17
  gem.add_dependency "activesupport", ">= 3.0.0"
18
18
  end
@@ -12,7 +12,7 @@ module DirtyAttributes
12
12
  end
13
13
 
14
14
  def attributes
15
- @attrs || []
15
+ @attrs
16
16
  end
17
17
  end
18
18
 
@@ -20,15 +20,17 @@ module DirtyAttributes
20
20
  attr_reader :attributes
21
21
 
22
22
  def initialize
23
- attrs = self.class.attributes.inject({}){|h, a| h.merge({a => nil})}
24
- @attributes = DirtyHashy.new(attrs).tap do |hashy|
25
- dirty_map! hashy, attrs.keys
23
+ @attributes = DirtyHashy.new({}, true, self.class.attributes).tap do |hashy|
24
+ dirty_map! hashy
26
25
  clean_up!
27
26
  end
28
27
  end
29
28
 
30
29
  def attributes=(other)
31
- attributes.clear.merge! other
30
+ attributes.replace other
31
+ rescue IndexError => e
32
+ e.message.match /"(.*)"/
33
+ raise NoMethodError, "undefined method `#{$1}=' for #{self.inspect}"
32
34
  end
33
35
  end
34
36
 
data/lib/dirty_hashy.rb CHANGED
@@ -5,18 +5,36 @@ require "method_map"
5
5
 
6
6
  class DirtyHashy < HashWithIndifferentAccess
7
7
 
8
- def self.new(constructor = {}, map_methods = false)
9
- super(constructor).tap do |instance|
10
- if map_methods
11
- instance.extend MethodMap
12
- instance.dirty_map!
13
- end
8
+ def initialize(constructor = {}, map_methods = false, restricted_keys = nil)
9
+ super constructor
10
+ if map_methods
11
+ extend MethodMap
12
+ dirty_map!
14
13
  end
14
+ if restricted_keys
15
+ restricted_keys.each{|key| self[key] ||= nil}
16
+ @restricted_keys = keys
17
+ end
18
+ end
19
+
20
+ def replace(other)
21
+ clear
22
+ merge! other
23
+ end
24
+
25
+ def clear
26
+ keys.each{|key| delete key}
27
+ end
28
+
29
+ def [](key, mapped = false)
30
+ validate_read!(key) if mapped || restricted_keys?
31
+ super(key)
15
32
  end
16
33
 
17
34
  alias :_regular_writer :regular_writer
18
35
  def regular_writer(key, value)
19
- original_value = changes.key?(key) ? was(key) : self[key]
36
+ validate_write!(key)
37
+ original_value = changes.key?(key) ? was(key) : fetch(key, nil)
20
38
  if original_value == value
21
39
  changes.delete key
22
40
  else
@@ -34,17 +52,18 @@ class DirtyHashy < HashWithIndifferentAccess
34
52
  @changes ||= HashWithIndifferentAccess.new
35
53
  end
36
54
 
37
- def changed?(key = nil)
55
+ def changed?(key = nil, mapped = false)
56
+ validate_read!(key) if !key.nil? && (mapped || restricted_keys?)
38
57
  key.nil? ? !changes.empty? : changes.key?(key)
39
58
  end
40
59
  alias :dirty? :changed?
41
60
 
42
- def change(key)
43
- changes[key] if changed?(key)
61
+ def change(key, mapped = false)
62
+ changes[key] if changed?(key, mapped)
44
63
  end
45
64
 
46
- def was(key)
47
- change(key).first if changed?(key)
65
+ def was(key, mapped = false)
66
+ change(key).first if changed?(key, mapped)
48
67
  end
49
68
 
50
69
  def clean_up!
@@ -52,4 +71,18 @@ class DirtyHashy < HashWithIndifferentAccess
52
71
  nil
53
72
  end
54
73
 
74
+ private
75
+
76
+ def restricted_keys?
77
+ !(@restricted_keys || []).empty?
78
+ end
79
+
80
+ def validate_read!(key)
81
+ raise IndexError, "Invalid key: \"#{key}\"" unless (keys + changes.keys).include?(key.to_s)
82
+ end
83
+
84
+ def validate_write!(key)
85
+ raise IndexError, "Invalid key: \"#{key}\"" unless @restricted_keys.nil? || @restricted_keys.empty? || @restricted_keys.include?(key.to_s)
86
+ end
87
+
55
88
  end
@@ -1,7 +1,7 @@
1
1
  class DirtyHashy < HashWithIndifferentAccess
2
2
  MAJOR = 0
3
3
  MINOR = 1
4
- TINY = 1
4
+ TINY = 2
5
5
 
6
6
  VERSION = [MAJOR, MINOR, TINY].join(".")
7
7
  end
data/lib/method_map.rb CHANGED
@@ -1,51 +1,44 @@
1
1
  module MethodMap
2
2
 
3
- def dirty_map!(mapped = nil, restricted_keys = nil)
3
+ def dirty_map!(mapped = nil)
4
4
  @mapped = mapped || self
5
- @restricted_keys = (restricted_keys || []).collect(&:to_s)
6
5
  map_method(:changes)
7
6
  map_method(:dirty?)
8
7
  map_method(:changed?)
9
8
  map_method(:clean_up!)
10
- map_method(/^([\w_]+)_changed\?$/, Proc.new{ |match| :changed? if map_key? match })
11
- map_method(/^([\w_]+)_change$/ , Proc.new{ |match| :change if map_key? match })
12
- map_method(/^([\w_]+)_was$/ , Proc.new{ |match| :was if map_key? match })
13
- map_method(/(^[\w_]+)=$/ , Proc.new{ |match| :[]= if accept_key? match })
14
- map_method(/(^[\w_]+)$/ , Proc.new{ |match| :[] if map_key? match })
9
+ map_method(/^([\w_]+)_changed\?$/, :changed?, true)
10
+ map_method(/^([\w_]+)_change$/, :change, true)
11
+ map_method(/^([\w_]+)_was$/, :was, true)
12
+ map_method(/(^[\w_]+)=$/, :[]=)
13
+ map_method(/(^[\w_]+)$/, :[], true)
15
14
  end
16
15
 
17
- def map_method(pattern, method_or_proc = nil)
16
+ def map_method(pattern, method_or_proc = nil, args = nil)
18
17
  regex = pattern.is_a?(Regexp) ? pattern : Regexp.new("^#{Regexp.escape(pattern.to_s)}$")
19
- method_map[regex] = method_or_proc || pattern
18
+ method_map[regex] = {:method_or_proc => (method_or_proc || pattern), :args => args}
20
19
  end
21
20
 
22
21
  def method_missing(method, *args)
23
22
  if m = match_method(method)
24
- @mapped.send *(m + args)
25
- else
26
- super
23
+ begin
24
+ return @mapped.send *(m + args)
25
+ rescue IndexError; end
27
26
  end
27
+ super
28
28
  end
29
29
 
30
30
  private
31
31
 
32
- def map_key?(key)
33
- (@mapped.keys + @mapped.changes.keys).include?(key.to_s)
34
- end
35
-
36
- def accept_key?(key)
37
- @restricted_keys.empty? || @restricted_keys.include?(key.to_s)
38
- end
39
-
40
32
  def method_map
41
33
  @method_map ||= {}
42
34
  end
43
35
 
44
36
  def match_method(method)
45
- method_map.each do |pattern, method_or_proc|
37
+ method_map.each do |pattern, spec|
38
+ method_or_proc = spec[:method_or_proc]
46
39
  if method.to_s.match pattern
47
40
  m = method_or_proc.is_a?(Proc) ? method_or_proc.call($1 || method) : method_or_proc
48
- return [m, $1].compact if m
41
+ return [m, $1, spec[:args]].compact if m
49
42
  end
50
43
  end
51
44
  nil
@@ -63,6 +63,38 @@ module Unit
63
63
  assert_equal nil, person.name_change
64
64
  assert_equal [nil, "Bar"], person.foo_change
65
65
  assert_equal({"foo" => [nil, "Bar"]}, person.changes)
66
+
67
+ person.attributes.merge! :company => "Internetbureau Holder B.V."
68
+
69
+ assert_equal true, person.dirty?
70
+ assert_equal true, person.changed?
71
+ assert_equal false, person.name_changed?
72
+ assert_equal true, person.foo_changed?
73
+ assert_equal true, person.company_changed?
74
+ assert_equal nil, person.name_change
75
+ assert_equal [nil, "Bar"], person.foo_change
76
+ assert_equal [nil, "Internetbureau Holder B.V."], person.company_change
77
+ assert_equal({"foo" => [nil, "Bar"], "company" => [nil, "Internetbureau Holder B.V."]}, person.changes)
78
+
79
+ person.attributes.delete :foo
80
+ person.clean_up!
81
+
82
+ assert_equal false, person.dirty?
83
+ assert_equal false, person.changed?
84
+ assert_equal({"name" => "Stephan", "company" => "Internetbureau Holder B.V."}, person.attributes)
85
+ assert_equal({}, person.changes)
86
+
87
+ person.attributes = {"name" => "Paul", "city" => "Amsterdam"}
88
+
89
+ assert_equal true, person.dirty?
90
+ assert_equal true, person.changed?
91
+ assert_equal true, person.name_changed?
92
+ assert_equal true, person.company_changed?
93
+ assert_equal true, person.city_changed?
94
+ assert_equal ["Stephan", "Paul"], person.name_change
95
+ assert_equal ["Internetbureau Holder B.V.", nil], person.company_change
96
+ assert_equal [nil, "Amsterdam"], person.city_change
97
+ assert_equal({"name" => ["Stephan", "Paul"], "company" => ["Internetbureau Holder B.V.", nil], "city" => [nil, "Amsterdam"]}, person.changes)
66
98
  end
67
99
 
68
100
  it "should behave as expected with key restriction" do
@@ -119,6 +151,22 @@ module Unit
119
151
  assert_equal false, user.name_changed?
120
152
  assert_equal nil, user.name_change
121
153
  assert_equal({}, user.changes)
154
+
155
+ user.attributes = {"name" => "Paul"}
156
+
157
+ assert_equal true, user.dirty?
158
+ assert_equal true, user.changed?
159
+ assert_equal true, user.name_changed?
160
+ assert_equal ["Stephan", "Paul"], user.name_change
161
+ assert_equal({"name" => ["Stephan", "Paul"]}, user.changes)
162
+
163
+ assert_raises(NoMethodError) do
164
+ user.attributes = {"company" => "Internetbureau Holder B.V."}
165
+ end
166
+
167
+ assert_raises(IndexError) do
168
+ user.attributes.merge! "company" => "Internetbureau Holder B.V."
169
+ end
122
170
  end
123
171
  end
124
172
 
@@ -4,9 +4,10 @@ module Unit
4
4
  class TestDirtyHashy < MiniTest::Unit::TestCase
5
5
 
6
6
  describe DirtyHashy do
7
- it "should behave as expected without method mapping" do
7
+ it "should behave as expected without method mapping and without restricted keys" do
8
8
  hashy = DirtyHashy.new
9
9
 
10
+ assert_equal({}, hashy)
10
11
  assert_equal false, hashy.dirty?
11
12
  assert_equal false, hashy.changed?
12
13
  assert_equal({}, hashy.changes)
@@ -137,11 +138,159 @@ module Unit
137
138
  assert_equal "Holder", hashy.was("company")
138
139
  assert_equal ["Holder", nil], hashy.change(:company)
139
140
  assert_equal ["Holder", nil], hashy.change("company")
141
+
142
+ hashy.merge! :name => "Paul", :company => "Internetbureau Holder B.V."
143
+
144
+ assert_equal true, hashy.dirty?
145
+ assert_equal true, hashy.changed?
146
+ assert_equal true, hashy.changed?(:name)
147
+ assert_equal true, hashy.changed?("name")
148
+ assert_equal true, hashy.changed?(:company)
149
+ assert_equal true, hashy.changed?("company")
150
+ assert_equal ["Tim", "Paul"], hashy.change(:name)
151
+ assert_equal ["Tim", "Paul"], hashy.change("name")
152
+ assert_equal ["Holder", "Internetbureau Holder B.V."], hashy.change(:company)
153
+ assert_equal ["Holder", "Internetbureau Holder B.V."], hashy.change("company")
154
+ assert_equal({"name" => ["Tim", "Paul"], "company" => ["Holder", "Internetbureau Holder B.V."]}, hashy.changes)
155
+ end
156
+
157
+ it "should behave as expected without method mapping, but with restricted keys" do
158
+ hashy = DirtyHashy.new({}, false, [:name])
159
+
160
+ assert_equal({"name" => nil}, hashy)
161
+ assert_equal false, hashy.dirty?
162
+ assert_equal false, hashy.changed?
163
+ assert_equal({}, hashy.changes)
164
+
165
+ assert_raises(NoMethodError) do
166
+ hashy.name = "Paul"
167
+ end
168
+
169
+ hashy["name"] = "Paul"
170
+
171
+ assert_equal true, hashy.dirty?
172
+ assert_equal true, hashy.changed?
173
+ assert_equal true, hashy.changed?(:name)
174
+ assert_equal true, hashy.changed?("name")
175
+ assert_equal [nil, "Paul"], hashy.change(:name)
176
+ assert_equal [nil, "Paul"], hashy.change("name")
177
+ assert_equal({"name" => [nil, "Paul"]}, hashy.changes)
178
+
179
+ hashy[:name] = nil
180
+
181
+ assert_equal false, hashy.dirty?
182
+ assert_equal false, hashy.changed?
183
+ assert_equal false, hashy.changed?(:name)
184
+ assert_equal false, hashy.changed?("name")
185
+ assert_equal nil, hashy.change(:name)
186
+ assert_equal nil, hashy.change("name")
187
+ assert_equal({}, hashy.changes)
188
+
189
+ hashy[:name] = "Stephan"
190
+
191
+ assert_equal true, hashy.dirty?
192
+ assert_equal true, hashy.changed?
193
+ assert_equal true, hashy.changed?(:name)
194
+ assert_equal true, hashy.changed?("name")
195
+ assert_equal [nil, "Stephan"], hashy.change(:name)
196
+ assert_equal [nil, "Stephan"], hashy.change("name")
197
+ assert_equal({"name" => [nil, "Stephan"]}, hashy.changes)
198
+
199
+ hashy.clean_up!
200
+
201
+ assert_equal false, hashy.dirty?
202
+ assert_equal false, hashy.changed?
203
+ assert_equal false, hashy.changed?(:name)
204
+ assert_equal false, hashy.changed?("name")
205
+ assert_equal nil, hashy.change(:name)
206
+ assert_equal nil, hashy.change("name")
207
+ assert_equal({}, hashy.changes)
208
+
209
+ hashy["name"] = "Chris"
210
+
211
+ assert_equal true, hashy.dirty?
212
+ assert_equal true, hashy.changed?
213
+ assert_equal true, hashy.changed?(:name)
214
+ assert_equal true, hashy.changed?("name")
215
+ assert_equal "Stephan", hashy.was("name")
216
+ assert_equal ["Stephan", "Chris"], hashy.change(:name)
217
+ assert_equal ["Stephan", "Chris"], hashy.change("name")
218
+ assert_equal({"name" => ["Stephan", "Chris"]}, hashy.changes)
219
+
220
+ hashy["name"] = "Stephan"
221
+
222
+ assert_equal false, hashy.dirty?
223
+ assert_equal false, hashy.changed?
224
+ assert_equal false, hashy.changed?(:name)
225
+ assert_equal false, hashy.changed?("name")
226
+ assert_equal nil, hashy.change(:name)
227
+ assert_equal nil, hashy.change("name")
228
+ assert_equal({}, hashy.changes)
229
+
230
+ hashy["name"] = "Paul"
231
+
232
+ assert_equal true, hashy.dirty?
233
+ assert_equal true, hashy.changed?
234
+ assert_equal true, hashy.changed?(:name)
235
+ assert_equal true, hashy.changed?("name")
236
+ assert_equal ["Stephan", "Paul"], hashy.change(:name)
237
+ assert_equal ["Stephan", "Paul"], hashy.change("name")
238
+ assert_equal({"name" => ["Stephan", "Paul"]}, hashy.changes)
239
+
240
+ hashy["name"] = "Tim"
241
+
242
+ assert_equal true, hashy.dirty?
243
+ assert_equal true, hashy.changed?
244
+ assert_equal true, hashy.changed?(:name)
245
+ assert_equal true, hashy.changed?("name")
246
+ assert_equal ["Stephan", "Tim"], hashy.change(:name)
247
+ assert_equal ["Stephan", "Tim"], hashy.change("name")
248
+ assert_equal({"name" => ["Stephan", "Tim"]}, hashy.changes)
249
+
250
+ hashy.clean_up!
251
+ hashy.merge! :name => "Paul"
252
+
253
+ assert_equal true, hashy.dirty?
254
+ assert_equal true, hashy.changed?
255
+ assert_equal true, hashy.changed?(:name)
256
+ assert_equal true, hashy.changed?("name")
257
+ assert_equal ["Tim", "Paul"], hashy.change(:name)
258
+ assert_equal ["Tim", "Paul"], hashy.change("name")
259
+ assert_equal({"name" => ["Tim", "Paul"]}, hashy.changes)
260
+
261
+ assert_raises(IndexError) do
262
+ hashy[:company]
263
+ end
264
+
265
+ assert_raises(IndexError) do
266
+ hashy["company"] = "Holder"
267
+ end
268
+
269
+ assert_raises(IndexError) do
270
+ hashy.delete :company
271
+ end
272
+
273
+ assert_raises(IndexError) do
274
+ hashy.changed? :company
275
+ end
276
+
277
+ assert_raises(IndexError) do
278
+ hashy.change :company
279
+ end
280
+
281
+ assert_raises(IndexError) do
282
+ hashy.was :company
283
+ end
284
+
285
+ assert_raises(IndexError) do
286
+ hashy.merge! :name => "Paul", :company => "Internetbureau Holder B.V."
287
+ end
140
288
  end
141
289
 
142
- it "should behave as expected with method mapping" do
290
+ it "should behave as expected with method mapping and without restricted keys" do
143
291
  hashy = DirtyHashy.new({}, true)
144
292
 
293
+ assert_equal({}, hashy)
145
294
  assert_equal false, hashy.dirty?
146
295
  assert_equal false, hashy.changed?
147
296
  assert_equal({}, hashy.changes)
@@ -225,10 +374,125 @@ module Unit
225
374
  hashy.delete :city
226
375
  assert_equal({"name" => ["Stephan", "Tim"]}, hashy.changes)
227
376
 
377
+ hashy.merge! :company => "Internetbureau Holder B.V."
378
+
379
+ assert_equal true, hashy.dirty?
380
+ assert_equal true, hashy.changed?
381
+ assert_equal true, hashy.changed?(:name)
382
+ assert_equal true, hashy.changed?("name")
383
+ assert_equal true, hashy.changed?(:company)
384
+ assert_equal true, hashy.changed?("company")
385
+ assert_equal ["Stephan", "Tim"], hashy.change(:name)
386
+ assert_equal ["Stephan", "Tim"], hashy.change("name")
387
+ assert_equal [nil, "Internetbureau Holder B.V."], hashy.change(:company)
388
+ assert_equal [nil, "Internetbureau Holder B.V."], hashy.change("company")
389
+ assert_equal({"name" => ["Stephan", "Tim"], "company" => [nil, "Internetbureau Holder B.V."]}, hashy.changes)
390
+
391
+ hashy.clean_up!
392
+
393
+ assert_equal false, hashy.dirty?
394
+ assert_equal false, hashy.changed?
395
+ end
396
+
397
+ it "should behave as expected with method mapping and with restricted keys" do
398
+ hashy = DirtyHashy.new({}, true, [:name])
399
+
400
+ assert_equal({"name" => nil}, hashy)
401
+ assert_equal nil, hashy.name
402
+ assert_equal false, hashy.dirty?
403
+ assert_equal false, hashy.changed?
404
+ assert_equal({}, hashy.changes)
405
+
406
+ hashy.name = "Paul"
407
+
408
+ assert_equal "Paul", hashy.name
409
+ assert_equal true, hashy.dirty?
410
+ assert_equal true, hashy.changed?
411
+ assert_equal true, hashy.name_changed?
412
+ assert_equal true, hashy.changed?(:name)
413
+ assert_equal [nil, "Paul"], hashy.name_change
414
+ assert_equal [nil, "Paul"], hashy.change(:name)
415
+ assert_equal({"name" => [nil, "Paul"]}, hashy.changes)
416
+
417
+ hashy.name = nil
418
+
419
+ assert_equal false, hashy.dirty?
420
+ assert_equal false, hashy.changed?
421
+ assert_equal false, hashy.name_changed?
422
+ assert_equal false, hashy.changed?(:name)
423
+ assert_equal nil, hashy.name_change
424
+ assert_equal nil, hashy.change(:name)
425
+ assert_equal({}, hashy.changes)
426
+
427
+ hashy.name = "Stephan"
428
+
429
+ assert_equal true, hashy.dirty?
430
+ assert_equal true, hashy.changed?
431
+ assert_equal true, hashy.name_changed?
432
+ assert_equal true, hashy.changed?(:name)
433
+ assert_equal [nil, "Stephan"], hashy.name_change
434
+ assert_equal [nil, "Stephan"], hashy.change(:name)
435
+ assert_equal({"name" => [nil, "Stephan"]}, hashy.changes)
436
+
228
437
  hashy.clean_up!
229
438
 
230
439
  assert_equal false, hashy.dirty?
231
440
  assert_equal false, hashy.changed?
441
+ assert_equal false, hashy.name_changed?
442
+ assert_equal false, hashy.changed?(:name)
443
+ assert_equal nil, hashy.name_change
444
+ assert_equal nil, hashy.change(:name)
445
+ assert_equal({}, hashy.changes)
446
+
447
+ hashy.name = "Chris"
448
+
449
+ assert_equal true, hashy.dirty?
450
+ assert_equal true, hashy.changed?
451
+ assert_equal true, hashy.name_changed?
452
+ assert_equal true, hashy.changed?(:name)
453
+ assert_equal "Stephan", hashy.name_was
454
+ assert_equal "Stephan", hashy.was(:name)
455
+ assert_equal ["Stephan", "Chris"], hashy.name_change
456
+ assert_equal ["Stephan", "Chris"], hashy.change(:name)
457
+ assert_equal({"name" => ["Stephan", "Chris"]}, hashy.changes)
458
+
459
+ hashy.name = "Stephan"
460
+
461
+ assert_equal false, hashy.dirty?
462
+ assert_equal false, hashy.changed?
463
+ assert_equal false, hashy.name_changed?
464
+ assert_equal false, hashy.changed?(:name)
465
+ assert_equal nil, hashy.name_change
466
+ assert_equal nil, hashy.change(:name)
467
+ assert_equal({}, hashy.changes)
468
+
469
+ assert_raises(NoMethodError) do
470
+ hashy.company
471
+ end
472
+
473
+ assert_raises(NoMethodError) do
474
+ hashy.company = "Holder"
475
+ end
476
+
477
+ assert_raises(IndexError) do
478
+ hashy.delete :company
479
+ end
480
+
481
+ assert_raises(NoMethodError) do
482
+ hashy.company_changed?
483
+ end
484
+
485
+ assert_raises(NoMethodError) do
486
+ hashy.company_change
487
+ end
488
+
489
+ assert_raises(NoMethodError) do
490
+ hashy.company_was
491
+ end
492
+
493
+ assert_raises(IndexError) do
494
+ hashy.merge! :name => "Paul", :company => "Internetbureau Holder B.V."
495
+ end
232
496
  end
233
497
  end
234
498
 
metadata CHANGED
@@ -1,35 +1,39 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: dirty_hashy
3
- version: !ruby/object:Gem::Version
4
- version: 0.1.1
3
+ version: !ruby/object:Gem::Version
5
4
  prerelease:
5
+ version: 0.1.2
6
6
  platform: ruby
7
- authors:
7
+ authors:
8
8
  - Paul Engel
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2011-12-24 00:00:00.000000000 Z
13
- dependencies:
14
- - !ruby/object:Gem::Dependency
12
+
13
+ date: 2011-12-24 00:00:00 +01:00
14
+ default_executable:
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
15
17
  name: activesupport
16
- requirement: &2152647000 !ruby/object:Gem::Requirement
18
+ prerelease: false
19
+ requirement: &id001 !ruby/object:Gem::Requirement
17
20
  none: false
18
- requirements:
19
- - - ! '>='
20
- - !ruby/object:Gem::Version
21
+ requirements:
22
+ - - ">="
23
+ - !ruby/object:Gem::Version
21
24
  version: 3.0.0
22
25
  type: :runtime
23
- prerelease: false
24
- version_requirements: *2152647000
25
- description: Dirty tracking within hashes with indifferent access or objects as it
26
- is expected to be!
27
- email:
26
+ version_requirements: *id001
27
+ description: Dirty tracking within hashes with indifferent access or objects as it is expected to be!
28
+ email:
28
29
  - paul.engel@holder.nl
29
30
  executables: []
31
+
30
32
  extensions: []
33
+
31
34
  extra_rdoc_files: []
32
- files:
35
+
36
+ files:
33
37
  - .gitignore
34
38
  - CHANGELOG.rdoc
35
39
  - Gemfile
@@ -46,32 +50,35 @@ files:
46
50
  - test/test_helper.rb
47
51
  - test/unit/test_dirty_attributes.rb
48
52
  - test/unit/test_dirty_hashy.rb
53
+ has_rdoc: true
49
54
  homepage: https://github.com/archan937/dirty_hashy
50
55
  licenses: []
56
+
51
57
  post_install_message:
52
58
  rdoc_options: []
53
- require_paths:
59
+
60
+ require_paths:
54
61
  - lib
55
- required_ruby_version: !ruby/object:Gem::Requirement
62
+ required_ruby_version: !ruby/object:Gem::Requirement
56
63
  none: false
57
- requirements:
58
- - - ! '>='
59
- - !ruby/object:Gem::Version
60
- version: '0'
61
- required_rubygems_version: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - ">="
66
+ - !ruby/object:Gem::Version
67
+ version: "0"
68
+ required_rubygems_version: !ruby/object:Gem::Requirement
62
69
  none: false
63
- requirements:
64
- - - ! '>='
65
- - !ruby/object:Gem::Version
66
- version: '0'
70
+ requirements:
71
+ - - ">="
72
+ - !ruby/object:Gem::Version
73
+ version: "0"
67
74
  requirements: []
75
+
68
76
  rubyforge_project:
69
- rubygems_version: 1.8.10
77
+ rubygems_version: 1.6.2
70
78
  signing_key:
71
79
  specification_version: 3
72
- summary: Dirty tracking within hashes with indifferent access or objects as it is
73
- expected to be!
74
- test_files:
80
+ summary: Dirty tracking within hashes with indifferent access or objects as it is expected to be!
81
+ test_files:
75
82
  - test/test_helper.rb
76
83
  - test/unit/test_dirty_attributes.rb
77
84
  - test/unit/test_dirty_hashy.rb