representable 1.3.1 → 1.3.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.
@@ -1,3 +1,7 @@
1
+ h2. 1.3.2
2
+
3
+ * Some minor internal changes. Added `Config#inherit` to encasulate array push behavior.
4
+
1
5
  h2. 1.3.1
2
6
 
3
7
  * Bringing back `:as`. For some strange reasons "we" lost that commit from @csexton!!!
data/README.md CHANGED
@@ -55,6 +55,19 @@ It also adds support for parsing.
55
55
  song = Song.new.extend(SongRepresenter).from_json(%{ {"title":"Roxanne"} })
56
56
  #=> #<Song title="Roxanne", track=nil>
57
57
 
58
+ ## Aliasing
59
+
60
+ If your property name doesn't match the name in the document, use the `:as` option.
61
+
62
+ module SongRepresenter
63
+ include Representable::JSON
64
+
65
+ property :title, as: :name
66
+ property :track
67
+ end
68
+
69
+ song.to_json #=> {"name":"Fallout","track":1}
70
+
58
71
 
59
72
  ## Wrapping
60
73
 
@@ -436,18 +449,6 @@ You can also define conditions on properties using `:if`, making them being cons
436
449
  When rendering or parsing, the `track` property is considered only if track is valid. Note that the block is executed in instance context, giving you access to instance methods.
437
450
 
438
451
 
439
- ### Mapping
440
-
441
- If your property name doesn't match the attribute name in the document, use the `:as` option.
442
-
443
- module SongRepresenter
444
- property :title
445
- property :track, as: :track_number
446
- end
447
-
448
- song.to_json #=> {"title":"Superstars","track_number":1}
449
-
450
-
451
452
  ### False and Nil Values
452
453
 
453
454
  Since representable-1.2 `false` values _are_ considered when parsing and rendering. That particularly means properties that used to be unset (i.e. `nil`) after parsing might be `false` now. Vice versa, `false` properties that weren't included in the rendered document will be visible now.
@@ -121,7 +121,7 @@ private
121
121
  module ClassInclusions
122
122
  def included(base)
123
123
  super
124
- base.representable_attrs.push(*representable_attrs.clone) # "inherit".
124
+ base.representable_attrs.inherit(representable_attrs)
125
125
  end
126
126
  end
127
127
 
@@ -145,7 +145,7 @@ private
145
145
 
146
146
  module Declarations
147
147
  def representable_attrs
148
- @representable_attrs ||= Config.new
148
+ @representable_attrs ||= build_config
149
149
  end
150
150
 
151
151
  def representation_wrap=(name)
@@ -190,10 +190,15 @@ private
190
190
  def definition_class
191
191
  Definition
192
192
  end
193
+
194
+ def build_config
195
+ Config.new
196
+ end
193
197
  end
194
198
  end
195
199
 
196
200
 
201
+ # NOTE: the API of Config is subject to change so don't rely too much on this private object.
197
202
  class Config < Array
198
203
  attr_accessor :wrap
199
204
 
@@ -207,7 +212,11 @@ private
207
212
  def clone
208
213
  self.class.new(collect { |d| d.clone })
209
214
  end
210
-
215
+
216
+ def inherit(parent)
217
+ push(*parent.clone)
218
+ end
219
+
211
220
  private
212
221
  def infer_name_for(name)
213
222
  name.to_s.split('::').last.
@@ -63,13 +63,15 @@ module Representable
63
63
  class HashBinding < PropertyBinding
64
64
  def serialize_for(value)
65
65
  # requires value to respond to #each with two block parameters.
66
- {}.tap do |hash|
67
- value.each { |key, obj| hash[key] = serialize(obj) }
66
+ {}.tap do |hsh|
67
+ value.each { |key, obj| hsh[key] = serialize(obj) }
68
68
  end
69
69
  end
70
70
 
71
71
  def deserialize_from(fragment)
72
- fragment.each { |key, item_fragment| fragment[key] = deserialize(item_fragment) }
72
+ {}.tap do |hsh|
73
+ fragment.each { |key, item_fragment| hsh[key] = deserialize(item_fragment) }
74
+ end
73
75
  end
74
76
  end
75
77
  end
@@ -1,3 +1,3 @@
1
1
  module Representable
2
- VERSION = "1.3.1"
2
+ VERSION = "1.3.2"
3
3
  end
@@ -460,8 +460,18 @@ end
460
460
  OpenStruct.new(:songs => {"7" => Song.new("Contemplation")}).extend(representer).to_hash.must_equal("songs"=>{"7"=>{"name"=>"Contemplation"}})
461
461
  end
462
462
 
463
- it "parses" do
464
- OpenStruct.new.extend(representer).from_hash("songs"=>{"7"=>{"name"=>"Contemplation"}}).songs.must_equal({"7"=>Song.new("Contemplation")})
463
+ describe "parsing" do
464
+ subject { OpenStruct.new.extend(representer) }
465
+ let (:hash) { {"7"=>{"name"=>"Contemplation"}} }
466
+
467
+ it "parses incoming hash" do
468
+ subject.from_hash("songs"=>hash).songs.must_equal({"7"=>Song.new("Contemplation")})
469
+ end
470
+
471
+ it "doesn't modify the incoming hash" do
472
+ subject.from_hash("songs"=> incoming_hash = hash.dup)
473
+ hash.must_equal incoming_hash
474
+ end
465
475
  end
466
476
  end
467
477
  end
@@ -571,31 +571,29 @@ class RepresentableTest < MiniTest::Spec
571
571
  end
572
572
 
573
573
  describe "Config" do
574
- before do
575
- @config = Representable::Config.new
576
- PunkRock = Class.new
577
- end
574
+ subject { Representable::Config.new }
575
+ PunkRock = Class.new
578
576
 
579
577
  describe "wrapping" do
580
578
  it "returns false per default" do
581
- assert_equal nil, @config.wrap_for("Punk")
579
+ assert_equal nil, subject.wrap_for("Punk")
582
580
  end
583
581
 
584
582
  it "infers a printable class name if set to true" do
585
- @config.wrap = true
586
- assert_equal "punk_rock", @config.wrap_for(PunkRock)
583
+ subject.wrap = true
584
+ assert_equal "punk_rock", subject.wrap_for(PunkRock)
587
585
  end
588
586
 
589
587
  it "can be set explicitely" do
590
- @config.wrap = "Descendents"
591
- assert_equal "Descendents", @config.wrap_for(PunkRock)
588
+ subject.wrap = "Descendents"
589
+ assert_equal "Descendents", subject.wrap_for(PunkRock)
592
590
  end
593
591
  end
594
592
 
595
593
  describe "clone" do
596
594
  it "clones all definitions" do
597
- @config << Object.new
598
- assert @config.first != @config.clone.first
595
+ subject << Object.new
596
+ assert subject.first != subject.clone.first
599
597
  end
600
598
  end
601
599
  end
@@ -62,4 +62,15 @@ MiniTest::Spec.class_eval do
62
62
  end
63
63
  end
64
64
  end
65
+
66
+ module TestMethods
67
+ def representer_for(modules=[Representable::Hash], &block)
68
+ Module.new do
69
+ extend TestMethods
70
+ include *modules
71
+ module_exec(&block)
72
+ end
73
+ end
74
+ end
75
+ include TestMethods
65
76
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: representable
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.1
4
+ version: 1.3.2
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-01-30 00:00:00.000000000 Z
12
+ date: 2013-02-12 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: nokogiri