representable 0.10.0 → 0.10.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,3 +1,8 @@
1
+ h2. 0.10.1
2
+
3
+ * The block in @to_*@ and @from_*@ now yields the symbolized property name. If you need the binding/definition you gotta get it yourself.
4
+ * Runs with Ruby 1.8 and 1.9.
5
+
1
6
  h2. 0.10.0
2
7
 
3
8
  * Wrapping can now be set through @Representable.representation_wrap=@. Possible values are:
@@ -5,9 +5,9 @@
5
5
 
6
6
  == Introduction
7
7
 
8
- _Representable_ maps fragments in documents to attributes in Ruby objects and back. It allows parsing representations and gives an object-oriented interface to the document. But that's only half of it! Representable can also render documents from an object instance.
8
+ _Representable_ maps fragments in documents to attributes in Ruby objects and back. It allows parsing representations giving an object-oriented interface to the document. But that's only half of it! Representable can also render documents from an object instance.
9
9
 
10
- This is especially helpful when implementing REST services and clients and keeps your representation knowledge in one place.
10
+ This keeps your representation knowledge in one place when implementing REST services and clients.
11
11
 
12
12
 
13
13
  == Features
@@ -19,86 +19,202 @@ This is especially helpful when implementing REST services and clients and keeps
19
19
 
20
20
  == Example
21
21
 
22
+ Since you keep forgetting the heroes of your childhood you decide to implement a REST service for storing and querying those. You choose representable for handling representations.
22
23
 
24
+ gem 'representable'
23
25
 
24
- When writing a REST service you'd have to parse and extract data from an incoming representation document manually. Given the following XML document which represents an order.
25
26
 
26
- <order>
27
- <id>1</id>
28
- <item>
29
- <name>Chocolate Cookie</name>
30
- </item>
31
- <item>
32
- <name>Vanilla Muffin</name>
33
- </item>
34
- </order>
27
+ == Defining Representations
35
28
 
36
- Now, parsing manually starts simple but gets complex soon. In the end, you have a nested hash data structure. Try this with Representable.
29
+ require 'representable/json'
37
30
 
38
- class Order
39
- include Representable::XML
31
+ class Hero
32
+ include Representable::JSON
40
33
 
41
- representable_property :id
42
- representable_collection :items, :from => :item, :as => Item
34
+ representable_property :forename
35
+ representable_property :surename
43
36
  end
37
+
38
+ This declares two simple properties. Representable will automatically add accessors to the class.
39
+
40
+ == Rendering
41
+
42
+ Now let's create and render our first hero.
43
+
44
+ peter = Hero.new
45
+ peter.forename = "Peter"
46
+ peter.surename = "Pan"
47
+
48
+ peter.to_json
49
+ #=> {"forename":"Peter","surename":"Pan"}
50
+
51
+ Those two properties are considered when rendering in #to_json.
52
+
53
+ == Parsing
54
+
55
+ The cool thing about Representable is: it works bidirectional. By declaring properties you can not only render but also parse!
56
+
57
+ hook = Hero.from_json('{"forename":"Captain","surename":"Hook"}')
58
+ hook.forename #=> "Captain"
44
59
 
45
- class Item
46
- include Representable::XML
60
+ See how easy this is? You can use an object-oriented method to read from the document.
61
+
62
+ == Nesting
63
+
64
+ You need a second domain object. Every hero has a place he comes from.
65
+
66
+ class Location
67
+ include Representable::JSON
47
68
 
48
- representable_property :name
69
+ representable_property :title
49
70
  end
50
-
51
- == Consuming Representations
52
71
 
53
- Representable gives you easy access for consuming incoming representation documents. It maps the appropriate content to objects' attributes.
72
+ Peter, where ya' from?
73
+
74
+ neverland = Location.new
75
+ neverland.title = "Neverland"
76
+
77
+ It makes sense to embed the location in the hero's document.
54
78
 
55
- @order = Order.from_xml(xml)
56
- @order.id # => "1"
57
- @order.items # => [<item>, <item>]
58
- @order.items.first.name # => "Chocolate Cookie"
79
+ class Hero
80
+ representable_property :origin, :as => Location
81
+ end
59
82
 
83
+ Using the +:as+ option allows you to include other representable objects.
60
84
 
61
- == Extendability
85
+ peter.origin = neverland
86
+ peter.to_json
87
+ #=> {"forename":"Peter","surename":"Pan","origin":{"title":"Neverland"}}
62
88
 
63
- The cool thing with object-oriented representations is: you can treat them just like any other object in Ruby and extend them dynamically - which is impossible with plain hashes.
64
89
 
65
- class Order
66
- # ...
67
-
68
- def sort_items
69
- items.sort! { |a, b| a.name <=> b.name }
70
- end
90
+ == Parsing Nested Documents
91
+
92
+ Don't forget how easy it is to parse nested representations.
93
+
94
+ hook = Hero.from_json('{"name":"Captain","surename":"Hook","origin":{"title":"Dark Ocean"}}')
95
+ hook.origin.inspect #=> #<Location:0x910d7c8 @title="Dark Ocean">
96
+ hook.origin.title #=> "Dark Ocean"
97
+
98
+ Representable just creates objects from the parsed document - nothing more and nothing less.
99
+
100
+ == Simple Collections
101
+
102
+ Heroes have features, special abilities that make 'em a superhero.
103
+
104
+ class Hero
105
+ representable_collection :features
106
+ end
107
+
108
+ The second API method is +representable_collection+ and, well, declares a collection.
109
+
110
+ peter.features = ["stays young", "can fly"]
111
+ peter.to_json
112
+ #=> {"forename":"Peter","surename":"Pan","origin":{"title":"Neverland"},"features":["stays young","can fly"]}
113
+
114
+
115
+ == Typed Collections
71
116
 
117
+ Ok, things start working out. Your hero has a name, an origin and a list of features so far. Why not allows adding friends to Peter - nobody wants to be alone!
72
118
 
73
- == Generating Representations
119
+ class Hero
120
+ representable_collection :friends, :as => Hero
121
+ end
122
+
123
+ Again, we type the collection by using the +:as+ option.
124
+
125
+ nick = Hero.new
126
+ nick.forename = "Nick"
127
+
128
+ el = Hero.new
129
+ el.forename = "El"
130
+
131
+ peter.friends = [nick, el]
132
+
133
+ I always wanted to be Peter's bro... in this example it is possible!
134
+
135
+ peter.to_json
136
+ #=> {"forename":"Peter","surename":"Pan","origin":{"title":"Neverland"},"features":["stays young","can fly"],"friends":[{"name":"Nick"},{"name":"El"}]}
137
+
138
+
139
+ == Customizing
140
+
141
+ === Wrapping
142
+
143
+ Representable is designed to be very simple. However, a few tweaks are available. What if you want to wrap your document?
144
+
145
+ class Hero
146
+ self.representation_wrap = true
147
+ end
148
+
149
+ peter.to_json #=> {"hero":{"name":"Peter","surename":"Pan"}}
150
+
151
+ You can also provide a custom wrapper.
74
152
 
75
- Usually you have two places that share knowledge about a representation and its syntax and semantics: the parser <em>and</em> the renderer. With Representable, this is kept in one place.
153
+ class Hero
154
+ self.representation_wrap = :boy
155
+ end
156
+
157
+ peter.to_json #=> {"boy":{"name":"Peter","surename":"Pan"}}
158
+
159
+
160
+ === Mapping
76
161
 
77
- @order.to_xml # => "<order><id>1</id>...</order>"
162
+ If your accessor name doesn't match the attribute name in the document, use the +:from+ matcher.
163
+
164
+ class Hero
165
+ representable_property :forename, :from => :name
166
+ end
78
167
 
79
- You can also render a representation from a newly created object.
168
+ peter.to_json #=> {"name":"Peter","surename":"Pan"}
80
169
 
81
- Order.new(:id => 2, :items => [candy]).to_xml
82
170
 
171
+ === Filtering
83
172
 
84
- Representable makes working with representations extremely easy and testable.
173
+ Representable allows you to skip properties when rendering or parsing.
85
174
 
175
+ peter.to_json do |name|
176
+ name == :forename
177
+ end
86
178
 
87
- == Serialization Backends
179
+ #=> {"forename":"Peter"}
88
180
 
89
- This gem ships with JSON and XML support, meaning you can parse and render both media formats.
181
+
182
+ == XML support
183
+
184
+ Representable allows declaring a document's syntax and structure while having different formats. Currently, it ships with JSON and XML bindings.
185
+
186
+ class Hero
187
+ include Representable::XML
188
+ end
189
+
190
+ peter.to_xml
191
+ #=> <hero>
192
+ <name>Peter</name>
193
+ <surename>Pan</surename>
194
+ <location>
195
+ <title>Neverland</title>
196
+ </location>
197
+ <hero>
198
+ <name>Nick</name>
199
+ </hero>
200
+ <hero>
201
+ <name>El</name>
202
+ </hero>
203
+ </hero>
204
+
205
+ The #to_xml method gives us an XML representation of Peter - great!
90
206
 
91
207
 
92
208
  == More
93
209
 
94
- Representable was written with REST representations in mind. However, it is a generic module for working with documents. If you do consider using it for a REST project, check out the {Roar framework}[http://github.com/apotonick/roar], which comes with representers, built-in hypermedia support and more. It internally uses Representable and streamlines the process for building hypermedia-driven REST applications.
210
+ Instead of spreading knowledge about your representations about the entire framework, Representable keeps rendering and parsing representations in one single, testable asset. It is a new abstraction layer missing in many "RESTful" frameworks.
95
211
 
96
- Representable comes with parser and renderer for XML and JSON and can easily be extended (Warning: internal API still changing).
212
+ Representable was written with REST representations in mind. However, it is a generic module for working with documents. If you do consider using it for a REST project, check out the {Roar framework}[http://github.com/apotonick/roar], which comes with representers, built-in hypermedia support and more. It internally uses Representable and streamlines the process for building hypermedia-driven REST applications.
97
213
 
98
214
 
99
215
  == Copyright
100
216
 
101
- Representable is a simplified fork of the ROXML gem. Big thanks to Ben Woosley for his work.
217
+ Representable is a heavily simplified fork of the ROXML gem. Big thanks to Ben Woosley for his work.
102
218
 
103
- Copyright (c) 2011 Nick Sutterer <apotonick@gmail.com>
104
- Copyright (c) 2004-2009 Ben Woosley, Zak Mandhro and Anders Engstrom.
219
+ * Copyright (c) 2011 Nick Sutterer <apotonick@gmail.com>
220
+ * Copyright (c) 2004-2009 Ben Woosley, Zak Mandhro and Anders Engstrom.
@@ -16,28 +16,35 @@ module Representable
16
16
  end
17
17
 
18
18
  # Reads values from +doc+ and sets properties accordingly.
19
- def update_properties_from(doc)
20
- self.class.representable_bindings.each do |ref|
21
- next if block_given? and not yield ref # skip if block is false. # DISCUSS: will we keep that?
19
+ def update_properties_from(doc, &block)
20
+ self.class.representable_bindings.each do |bin|
21
+ next if eval_property_block(bin, &block) # skip if block is false.
22
22
 
23
- value = ref.read(doc)
24
- send(ref.definition.setter, value)
23
+ value = bin.read(doc)
24
+ send(bin.definition.setter, value)
25
25
  end
26
26
  self
27
27
  end
28
28
 
29
29
  private
30
30
  # Compiles the document going through all properties.
31
- def create_representation_with(doc)
32
- self.class.representable_bindings.each do |ref|
33
- next if block_given? and not yield ref # skip if block is false. # DISCUSS: will we keep that?
31
+ def create_representation_with(doc, &block)
32
+ self.class.representable_bindings.each do |bin|
33
+ next if eval_property_block(bin, &block) # skip if block is false.
34
34
 
35
- value = public_send(ref.definition.getter) # DISCUSS: eventually move back to Ref.
36
- ref.write(doc, value) if value
35
+ value = send(bin.definition.getter) # DISCUSS: eventually move back to Ref.
36
+ bin.write(doc, value) if value
37
37
  end
38
38
  doc
39
39
  end
40
40
 
41
+ # Returns true unless a eventually given block returns false. Yields the symbolized
42
+ # property name.
43
+ def eval_property_block(binding)
44
+ # TODO: no magic symbol conversion!
45
+ block_given? and not yield binding.definition.name.to_sym
46
+ end
47
+
41
48
 
42
49
  module ClassMethods # :nodoc:
43
50
  module Declarations
@@ -1,5 +1,6 @@
1
- require 'json'
1
+ require 'representable'
2
2
  require 'representable/bindings/json_bindings'
3
+ require 'json'
3
4
 
4
5
  module Representable
5
6
  # Brings #to_xml, #to_hash, #from_xml and #from_hash to your object.
@@ -48,8 +49,8 @@ module Representable
48
49
  update_properties_from(data, &block)
49
50
  end
50
51
 
51
- def to_hash(options={})
52
- hash = create_representation_with({})
52
+ def to_hash(options={}, &block)
53
+ hash = create_representation_with({}, &block)
53
54
 
54
55
  return hash unless wrap = options[:wrap] || self.class.representation_wrap
55
56
 
@@ -57,8 +58,8 @@ module Representable
57
58
  end
58
59
 
59
60
  # Returns a JSON string representing this object.
60
- def to_json(options={})
61
- to_hash(options).to_json
61
+ def to_json(*args, &block)
62
+ to_hash(*args, &block).to_json
62
63
  end
63
64
  end
64
65
  end
@@ -1,3 +1,3 @@
1
1
  module Representable
2
- VERSION = "0.10.0"
2
+ VERSION = "0.10.1"
3
3
  end
@@ -1,5 +1,6 @@
1
1
  require 'representable'
2
2
  require 'representable/bindings/xml_bindings'
3
+ require 'nokogiri'
3
4
 
4
5
  module Representable
5
6
  module XML
@@ -8,142 +8,146 @@ module JsonTest
8
8
 
9
9
  describe "JSON module" do
10
10
  before do
11
- @Band = Class.new(Band) do
11
+ @Band = Class.new do
12
+ include Representable::JSON
13
+ representable_property :name
12
14
  representable_property :label
15
+
16
+ def initialize(name=nil)
17
+ self.name = name if name
18
+ end
13
19
  end
14
20
  end
15
-
16
- class Band
17
- include Representable::JSON
18
- representable_property :name
19
- end
20
-
21
- describe "#binding_for_definition" do
22
- it "returns ObjectBinding" do
23
- assert_kind_of Json::ObjectBinding, Band.binding_for_definition(Def.new(:band, :as => Hash))
24
- end
25
-
26
- it "returns TextBinding" do
27
- assert_kind_of Json::TextBinding, Band.binding_for_definition(Def.new(:band))
21
+
22
+
23
+ describe ".from_json" do
24
+ it "is delegated to #from_json" do
25
+ block = lambda {|bind|}
26
+ @Band.any_instance.expects(:from_json).with("{}", "yo") # FIXME: how to expect block?
27
+ @Band.from_json("{}", "yo", &block)
28
28
  end
29
29
  end
30
30
 
31
- describe "#representable_bindings" do
32
- it "returns bindings for each property" do
33
- assert_equal 1, Band.representable_bindings.size
34
- assert_equal "name", Band.representable_bindings.first.definition.name
31
+
32
+ describe ".from_hash" do
33
+ it "is delegated to #from_hash" do
34
+ block = lambda {|bind|}
35
+ @Band.any_instance.expects(:from_hash).with("{}", "yo") # FIXME: how to expect block?
36
+ @Band.from_hash("{}", "yo", &block)
35
37
  end
36
38
  end
37
39
 
40
+
38
41
  describe "#from_json" do
39
42
  before do
40
43
  @band = @Band.new
44
+ @json = {:name => "Nofx", :label => "NOFX"}.to_json
41
45
  end
42
46
 
43
- it "accepts json string" do
44
- @band.from_json({name: "Nofx", label: "NOFX"}.to_json)
47
+ it "parses JSON and assigns properties" do
48
+ @band.from_json(@json)
45
49
  assert_equal ["Nofx", "NOFX"], [@band.name, @band.label]
46
50
  end
47
51
 
48
- it "forwards block to #update_properties_from" do
49
- @band.from_json({name: "Nofx", label: "NOFX"}.to_json) do |binding|
50
- binding.definition.name == "name"
52
+ it "forwards block to #from_hash" do
53
+ @band.from_json(@json) do |name|
54
+ name == :name
51
55
  end
52
56
 
53
57
  assert_equal ["Nofx", nil], [@band.name, @band.label]
54
58
  end
59
+ end
60
+
61
+
62
+ describe "#from_hash" do
63
+ before do
64
+ @band = @Band.new
65
+ @hash = {"name" => "Nofx", "label" => "NOFX"}
66
+ end
55
67
 
68
+ it "receives hash and assigns properties" do
69
+ @band.from_hash(@hash)
70
+ assert_equal ["Nofx", "NOFX"], [@band.name, @band.label]
71
+ end
56
72
 
57
- it "doesn't use wrap per default" do
58
- @band.from_json({:name => "This Is A Standoff"}.to_json)
59
- assert_equal "This Is A Standoff", @band.name
73
+ it "forwards block to #update_properties_from" do
74
+ @band.from_hash(@hash) do |name|
75
+ name == :name
76
+ end
77
+
78
+ assert_equal ["Nofx", nil], [@band.name, @band.label]
60
79
  end
61
80
 
62
81
  it "respects :wrap option" do
63
- @band.from_json({:band => {:name => "This Is A Standoff"}}.to_json, :wrap => :band)
82
+ @band.from_hash({"band" => {"name" => "This Is A Standoff"}}, :wrap => :band)
64
83
  assert_equal "This Is A Standoff", @band.name
65
84
  end
66
-
85
+
67
86
  it "respects :wrap option over representation_wrap" do
68
87
  @Band.class_eval do
69
88
  self.representation_wrap = :group
70
89
  end
71
- @band.from_json({:band => {:name => "This Is A Standoff"}}.to_json, :wrap => :band)
72
- assert_equal "This Is A Standoff", @band.name
73
- end
74
-
75
- it "respects representation_wrap" do
76
- @Band.class_eval do
77
- self.representation_wrap = :group
78
- end
79
- @band.from_json({:group => {:name => "This Is A Standoff"}}.to_json)
90
+ @band.from_hash({"band" => {"name" => "This Is A Standoff"}}, :wrap => :band)
80
91
  assert_equal "This Is A Standoff", @band.name
81
92
  end
82
93
  end
83
94
 
84
95
 
85
- describe ".from_json" do
86
- it "delegates to #from_json after object conception" do
87
- band = @Band.from_json({name: "Nofx", label: "NOFX"}.to_json) do |binding| binding.definition.name == "name" end
88
- assert_equal ["Nofx", nil], [band.name, band.label]
89
- end
90
-
91
- it "passes all args to #from_json" do
92
- block = lambda {|a,b|}
93
- @Band.any_instance.expects(:from_json).with("{}", "yo") # FIXME: how to expect block?
94
- @Band.from_json("{}", "yo", &block)
96
+ describe "#to_json" do
97
+ it "delegates to #to_hash and returns string" do
98
+ assert_equal "{\"name\":\"Rise Against\"}", @Band.new("Rise Against").to_json
95
99
  end
96
100
 
97
- # TODO: move following tests to #from_json test.
98
- it "raises error with emtpy string" do
99
- assert_raises JSON::ParserError do
100
- Band.from_json("")
101
+ it "forwards block to #to_hash" do
102
+ band = @Band.new
103
+ band.name = "The Guinea Pigs"
104
+ band.label = "n/a"
105
+ json = band.to_json do |name|
106
+ name == :name
101
107
  end
102
- end
103
-
104
- it "returns empty hash with inappropriate hash" do
105
- assert Band.from_json({:song => "Message In A Bottle"}.to_json)
106
- end
107
-
108
- it "generates warning with inappropriate hash in debugging mode" do
108
+
109
+ assert_equal "{\"name\":\"The Guinea Pigs\"}", json
109
110
  end
110
111
  end
111
112
 
112
113
 
113
- describe ".from_hash" do
114
- it "accepts unwrapped hash with string keys" do
115
- band = Band.from_hash("name" => "Bombshell Rocks")
116
- assert_equal "Bombshell Rocks", band.name
117
- end
118
- end
119
-
120
-
121
- describe "#to_json" do
122
- before do
123
- @band = @Band.new
124
- @band.label = "Fat"
114
+ describe "#to_hash" do
115
+ it "returns unwrapped hash" do
116
+ hash = @Band.new("Rise Against").to_hash
117
+ assert_equal({"name"=>"Rise Against"}, hash)
125
118
  end
126
119
 
127
- it "doesn't wrap per default" do
128
- assert_equal "{\"label\":\"Fat\"}", @band.to_json
120
+ it "respects #representation_wrap=" do
121
+ @Band.representation_wrap = :group
122
+ assert_equal({:group=>{"name"=>"Rise Against"}}, @Band.new("Rise Against").to_hash)
129
123
  end
130
124
 
131
125
  it "respects :wrap option" do
132
- assert_equal "{\"band\":{\"label\":\"Fat\"}}", @band.to_json(:wrap => :band)
126
+ assert_equal({:band=>{"name"=>"NOFX"}}, @Band.new("NOFX").to_hash(:wrap => :band))
133
127
  end
134
-
128
+
135
129
  it "respects :wrap option over representation_wrap" do
136
130
  @Band.class_eval do
137
131
  self.representation_wrap = :group
138
132
  end
139
- assert_equal "{\"band\":{\"label\":\"Fat\"}}", @band.to_json(:wrap => :band)
133
+ assert_equal({:band=>{"name"=>"Rise Against"}}, @Band.new("Rise Against").to_hash(:wrap => :band))
140
134
  end
135
+ end
141
136
 
142
- it "respects representation_wrap" do
143
- @Band.class_eval do
144
- self.representation_wrap = :group
145
- end
146
- assert_equal "{\"group\":{\"label\":\"Fat\"}}", @band.to_json
137
+ describe "#binding_for_definition" do
138
+ it "returns ObjectBinding" do
139
+ assert_kind_of Json::ObjectBinding, @Band.binding_for_definition(Def.new(:band, :as => Hash))
140
+ end
141
+
142
+ it "returns TextBinding" do
143
+ assert_kind_of Json::TextBinding, @Band.binding_for_definition(Def.new(:band))
144
+ end
145
+ end
146
+
147
+ describe "#representable_bindings" do
148
+ it "returns bindings for each property" do
149
+ assert_equal 2, @Band.representable_bindings.size
150
+ assert_equal "name", @Band.representable_bindings.first.definition.name
147
151
  end
148
152
  end
149
153
  end
@@ -116,8 +116,8 @@ class RepresentableTest < MiniTest::Spec
116
116
 
117
117
  it "skips elements when block returns false" do
118
118
  band = PopBand.new
119
- band.update_properties_from({"name"=>"No One's Choice", "groupies"=>2}) do |binding|
120
- binding.definition.name == "name"
119
+ band.update_properties_from({"name"=>"No One's Choice", "groupies"=>2}) do |name|
120
+ name == :name
121
121
  end
122
122
  assert_equal "No One's Choice", band.name
123
123
  assert_equal nil, band.groupies
@@ -141,7 +141,7 @@ class RepresentableTest < MiniTest::Spec
141
141
  end
142
142
 
143
143
  it "skips elements when block returns false" do
144
- assert_equal({"name"=>"No One's Choice"}, @band.send(:create_representation_with, {}) do |binding| binding.definition.name == "name" end)
144
+ assert_equal({"name"=>"No One's Choice"}, @band.send(:create_representation_with, {}) do |name| name == :name end)
145
145
  end
146
146
  end
147
147
 
@@ -1,8 +1,10 @@
1
1
  require 'bundler'
2
2
  Bundler.setup
3
3
 
4
+ gem 'minitest'
4
5
  require 'representable'
5
6
  require 'test/unit'
6
7
  require 'minitest/spec'
8
+ require 'minitest/autorun'
7
9
  require 'test_xml/mini_test'
8
10
  require 'mocha'
@@ -65,8 +65,8 @@ class XmlTest < MiniTest::Spec
65
65
  end
66
66
 
67
67
  it "forwards block to #from_node" do
68
- @band.from_xml(@xml) do |binding|
69
- binding.definition.name == "name"
68
+ @band.from_xml(@xml) do |name|
69
+ name == :name
70
70
  end
71
71
 
72
72
  assert_equal ["Nofx", nil], [@band.name, @band.label]
@@ -86,8 +86,8 @@ class XmlTest < MiniTest::Spec
86
86
  end
87
87
 
88
88
  it "forwards block to #update_properties_from" do
89
- @band.from_node(@xml) do |binding|
90
- binding.definition.name == "name"
89
+ @band.from_node(@xml) do |name|
90
+ name == :name
91
91
  end
92
92
 
93
93
  assert_equal ["Nofx", nil], [@band.name, @band.label]
@@ -104,8 +104,8 @@ class XmlTest < MiniTest::Spec
104
104
  band = @Band.new
105
105
  band.name = "The Guinea Pigs"
106
106
  band.label = "n/a"
107
- xml = band.to_xml do |binding|
108
- binding.definition.name == "name"
107
+ xml = band.to_xml do |name|
108
+ name == :name
109
109
  end
110
110
 
111
111
  assert_xml_equal "<band><name>The Guinea Pigs</name></band>", xml
metadata CHANGED
@@ -1,124 +1,101 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: representable
3
- version: !ruby/object:Gem::Version
4
- prerelease: false
5
- segments:
6
- - 0
7
- - 10
8
- - 0
9
- version: 0.10.0
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.10.1
5
+ prerelease:
10
6
  platform: ruby
11
- authors:
7
+ authors:
12
8
  - Nick Sutterer
13
9
  autorequire:
14
10
  bindir: bin
15
11
  cert_chain: []
16
-
17
- date: 2011-11-29 00:00:00 +01:00
18
- default_executable:
19
- dependencies:
20
- - !ruby/object:Gem::Dependency
12
+ date: 2011-12-01 00:00:00.000000000Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
21
15
  name: hooks
22
- prerelease: false
23
- requirement: &id001 !ruby/object:Gem::Requirement
16
+ requirement: &72137670 !ruby/object:Gem::Requirement
24
17
  none: false
25
- requirements:
26
- - - ">="
27
- - !ruby/object:Gem::Version
28
- segments:
29
- - 0
30
- version: "0"
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
31
22
  type: :runtime
32
- version_requirements: *id001
33
- - !ruby/object:Gem::Dependency
34
- name: nokogiri
35
23
  prerelease: false
36
- requirement: &id002 !ruby/object:Gem::Requirement
24
+ version_requirements: *72137670
25
+ - !ruby/object:Gem::Dependency
26
+ name: nokogiri
27
+ requirement: &72137450 !ruby/object:Gem::Requirement
37
28
  none: false
38
- requirements:
39
- - - ">="
40
- - !ruby/object:Gem::Version
41
- segments:
42
- - 0
43
- version: "0"
29
+ requirements:
30
+ - - ! '>='
31
+ - !ruby/object:Gem::Version
32
+ version: '0'
44
33
  type: :runtime
45
- version_requirements: *id002
46
- - !ruby/object:Gem::Dependency
47
- name: json
48
34
  prerelease: false
49
- requirement: &id003 !ruby/object:Gem::Requirement
35
+ version_requirements: *72137450
36
+ - !ruby/object:Gem::Dependency
37
+ name: json
38
+ requirement: &72137230 !ruby/object:Gem::Requirement
50
39
  none: false
51
- requirements:
52
- - - ">="
53
- - !ruby/object:Gem::Version
54
- segments:
55
- - 0
56
- version: "0"
40
+ requirements:
41
+ - - ! '>='
42
+ - !ruby/object:Gem::Version
43
+ version: '0'
57
44
  type: :runtime
58
- version_requirements: *id003
59
- - !ruby/object:Gem::Dependency
60
- name: rake
61
45
  prerelease: false
62
- requirement: &id004 !ruby/object:Gem::Requirement
46
+ version_requirements: *72137230
47
+ - !ruby/object:Gem::Dependency
48
+ name: rake
49
+ requirement: &72137010 !ruby/object:Gem::Requirement
63
50
  none: false
64
- requirements:
65
- - - ">="
66
- - !ruby/object:Gem::Version
67
- segments:
68
- - 0
69
- version: "0"
51
+ requirements:
52
+ - - ! '>='
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
70
55
  type: :development
71
- version_requirements: *id004
72
- - !ruby/object:Gem::Dependency
73
- name: test_xml
74
56
  prerelease: false
75
- requirement: &id005 !ruby/object:Gem::Requirement
57
+ version_requirements: *72137010
58
+ - !ruby/object:Gem::Dependency
59
+ name: test_xml
60
+ requirement: &72136800 !ruby/object:Gem::Requirement
76
61
  none: false
77
- requirements:
78
- - - ">="
79
- - !ruby/object:Gem::Version
80
- segments:
81
- - 0
82
- version: "0"
62
+ requirements:
63
+ - - ! '>='
64
+ - !ruby/object:Gem::Version
65
+ version: '0'
83
66
  type: :development
84
- version_requirements: *id005
85
- - !ruby/object:Gem::Dependency
86
- name: minitest
87
67
  prerelease: false
88
- requirement: &id006 !ruby/object:Gem::Requirement
68
+ version_requirements: *72136800
69
+ - !ruby/object:Gem::Dependency
70
+ name: minitest
71
+ requirement: &72136530 !ruby/object:Gem::Requirement
89
72
  none: false
90
- requirements:
73
+ requirements:
91
74
  - - ~>
92
- - !ruby/object:Gem::Version
93
- segments:
94
- - 2
95
- - 8
96
- version: "2.8"
75
+ - !ruby/object:Gem::Version
76
+ version: '2.8'
97
77
  type: :development
98
- version_requirements: *id006
99
- - !ruby/object:Gem::Dependency
100
- name: mocha
101
78
  prerelease: false
102
- requirement: &id007 !ruby/object:Gem::Requirement
79
+ version_requirements: *72136530
80
+ - !ruby/object:Gem::Dependency
81
+ name: mocha
82
+ requirement: &72136320 !ruby/object:Gem::Requirement
103
83
  none: false
104
- requirements:
105
- - - ">="
106
- - !ruby/object:Gem::Version
107
- segments:
108
- - 0
109
- version: "0"
84
+ requirements:
85
+ - - ! '>='
86
+ - !ruby/object:Gem::Version
87
+ version: '0'
110
88
  type: :development
111
- version_requirements: *id007
112
- description: Maps representation documents from and to Ruby objects. Includes XML and JSON support, plain properties and compositions.
113
- email:
89
+ prerelease: false
90
+ version_requirements: *72136320
91
+ description: Maps representation documents from and to Ruby objects. Includes XML
92
+ and JSON support, plain properties and compositions.
93
+ email:
114
94
  - apotonick@gmail.com
115
95
  executables: []
116
-
117
96
  extensions: []
118
-
119
97
  extra_rdoc_files: []
120
-
121
- files:
98
+ files:
122
99
  - .gitignore
123
100
  - .gitmodules
124
101
  - .rspec
@@ -142,37 +119,29 @@ files:
142
119
  - test/representable_test.rb
143
120
  - test/test_helper.rb
144
121
  - test/xml_test.rb
145
- has_rdoc: true
146
122
  homepage: http://representable.apotomo.de
147
123
  licenses: []
148
-
149
124
  post_install_message:
150
125
  rdoc_options: []
151
-
152
- require_paths:
126
+ require_paths:
153
127
  - lib
154
- required_ruby_version: !ruby/object:Gem::Requirement
128
+ required_ruby_version: !ruby/object:Gem::Requirement
155
129
  none: false
156
- requirements:
157
- - - ">="
158
- - !ruby/object:Gem::Version
159
- segments:
160
- - 0
161
- version: "0"
162
- required_rubygems_version: !ruby/object:Gem::Requirement
130
+ requirements:
131
+ - - ! '>='
132
+ - !ruby/object:Gem::Version
133
+ version: '0'
134
+ required_rubygems_version: !ruby/object:Gem::Requirement
163
135
  none: false
164
- requirements:
165
- - - ">="
166
- - !ruby/object:Gem::Version
167
- segments:
168
- - 0
169
- version: "0"
136
+ requirements:
137
+ - - ! '>='
138
+ - !ruby/object:Gem::Version
139
+ version: '0'
170
140
  requirements: []
171
-
172
141
  rubyforge_project:
173
- rubygems_version: 1.3.7
142
+ rubygems_version: 1.8.10
174
143
  signing_key:
175
144
  specification_version: 3
176
- summary: Maps representation documents from and to Ruby objects. Includes XML and JSON support, plain properties and compositions.
145
+ summary: Maps representation documents from and to Ruby objects. Includes XML and
146
+ JSON support, plain properties and compositions.
177
147
  test_files: []
178
-