make_resourceful_rails2 1.0.1

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.
Files changed (39) hide show
  1. data/Rakefile +31 -0
  2. data/VERSION +1 -0
  3. data/lib/make_resourceful.rb +2 -0
  4. data/lib/resourceful/base.rb +63 -0
  5. data/lib/resourceful/builder.rb +405 -0
  6. data/lib/resourceful/default/accessors.rb +418 -0
  7. data/lib/resourceful/default/actions.rb +101 -0
  8. data/lib/resourceful/default/callbacks.rb +51 -0
  9. data/lib/resourceful/default/responses.rb +118 -0
  10. data/lib/resourceful/default/urls.rb +136 -0
  11. data/lib/resourceful/generators/resourceful_scaffold/resourceful_scaffold_generator.rb +87 -0
  12. data/lib/resourceful/generators/resourceful_scaffold/templates/controller.rb +5 -0
  13. data/lib/resourceful/generators/resourceful_scaffold/templates/fixtures.yml +10 -0
  14. data/lib/resourceful/generators/resourceful_scaffold/templates/functional_test.rb +50 -0
  15. data/lib/resourceful/generators/resourceful_scaffold/templates/helper.rb +2 -0
  16. data/lib/resourceful/generators/resourceful_scaffold/templates/migration.rb +13 -0
  17. data/lib/resourceful/generators/resourceful_scaffold/templates/model.rb +2 -0
  18. data/lib/resourceful/generators/resourceful_scaffold/templates/unit_test.rb +7 -0
  19. data/lib/resourceful/generators/resourceful_scaffold/templates/view__form.haml +5 -0
  20. data/lib/resourceful/generators/resourceful_scaffold/templates/view_edit.haml +11 -0
  21. data/lib/resourceful/generators/resourceful_scaffold/templates/view_index.haml +5 -0
  22. data/lib/resourceful/generators/resourceful_scaffold/templates/view_new.haml +9 -0
  23. data/lib/resourceful/generators/resourceful_scaffold/templates/view_partial.haml +12 -0
  24. data/lib/resourceful/generators/resourceful_scaffold/templates/view_show.haml +14 -0
  25. data/lib/resourceful/maker.rb +92 -0
  26. data/lib/resourceful/response.rb +33 -0
  27. data/lib/resourceful/serialize.rb +185 -0
  28. data/spec/accessors_spec.rb +474 -0
  29. data/spec/actions_spec.rb +310 -0
  30. data/spec/base_spec.rb +12 -0
  31. data/spec/builder_spec.rb +332 -0
  32. data/spec/callbacks_spec.rb +71 -0
  33. data/spec/integration_spec.rb +394 -0
  34. data/spec/maker_spec.rb +91 -0
  35. data/spec/response_spec.rb +37 -0
  36. data/spec/responses_spec.rb +314 -0
  37. data/spec/serialize_spec.rb +133 -0
  38. data/spec/urls_spec.rb +282 -0
  39. metadata +114 -0
@@ -0,0 +1,91 @@
1
+ require File.dirname(__FILE__) + '/spec_helper'
2
+
3
+ describe Resourceful::Maker, "when extended" do
4
+ include ControllerMocks
5
+ before(:each) { mock_kontroller }
6
+
7
+ it "should create an empty, inheritable callbacks hash" do
8
+ @kontroller.resourceful_callbacks.should == {}
9
+ end
10
+
11
+ it "should create an empty, inheritable responses hash" do
12
+ @kontroller.resourceful_responses.should == {}
13
+ end
14
+
15
+ it "should create an empty, inheritable parents array" do
16
+ @kontroller.parents.should == []
17
+ end
18
+
19
+ it "should create a made_resourceful variable set to false" do
20
+ @kontroller.made_resourceful.should be_false
21
+ end
22
+
23
+ it "should create a made_resourceful? method on the controller that returns the variable" do
24
+ @kontroller.should_not be_made_resourceful
25
+ @kontroller.made_resourceful = true
26
+ @kontroller.should be_made_resourceful
27
+ end
28
+ end
29
+
30
+ describe Resourceful::Maker, "when made_resourceful" do
31
+ include ControllerMocks
32
+ before(:each) do
33
+ mock_kontroller
34
+ mock_builder
35
+ end
36
+
37
+ it "should include Resourceful::Base" do
38
+ @kontroller.expects(:include).with(Resourceful::Base)
39
+ @kontroller.make_resourceful {}
40
+ end
41
+
42
+ it "should use Resourceful::Builder to build the controller" do
43
+ Resourceful::Builder.expects(:new).with(@kontroller).returns(@builder)
44
+ @kontroller.make_resourceful {}
45
+ end
46
+
47
+ it "should evaluate the made_resourceful callbacks in the context of the builder" do
48
+ procs = (1..5).map { should_be_called { with(@builder) } }
49
+ Resourceful::Base.stubs(:made_resourceful).returns(procs)
50
+ @kontroller.make_resourceful {}
51
+ end
52
+
53
+ it "should evaluate the :include callback in the context of the builder" do
54
+ @kontroller.make_resourceful(:include => should_be_called { with(@builder) }) {}
55
+ end
56
+
57
+ it "should evaluate the given block in the context of the builder" do
58
+ @kontroller.make_resourceful(&(should_be_called { with(@builder) }))
59
+ end
60
+ end
61
+
62
+ describe Resourceful::Maker, "when made_resourceful with an inherited controller" do
63
+ include ControllerMocks
64
+ before(:each) do
65
+ mock_kontroller
66
+ mock_builder :inherited
67
+ end
68
+
69
+ it "should include Resourceful::Base" do
70
+ @kontroller.expects(:include).with(Resourceful::Base)
71
+ @kontroller.make_resourceful {}
72
+ end
73
+
74
+ it "should use Resourceful::Builder to build the controller" do
75
+ Resourceful::Builder.expects(:new).with(@kontroller).returns(@builder)
76
+ @kontroller.make_resourceful {}
77
+ end
78
+
79
+ it "should not evaluate the made_resourceful callbacks in the context of the builder" do
80
+ Resourceful::Base.expects(:made_resourceful).never
81
+ @kontroller.make_resourceful {}
82
+ end
83
+
84
+ it "should evaluate the :include callback in the context of the builder" do
85
+ @kontroller.make_resourceful(:include => should_be_called { with(@builder) }) {}
86
+ end
87
+
88
+ it "should evaluate the given block in the context of the builder" do
89
+ @kontroller.make_resourceful(&(should_be_called { with(@builder) }))
90
+ end
91
+ end
@@ -0,0 +1,37 @@
1
+ require File.dirname(__FILE__) + '/spec_helper'
2
+
3
+ describe Resourceful::Response, "when first created" do
4
+ before(:each) { @response = Resourceful::Response.new }
5
+
6
+ it "should have an empty formats array" do
7
+ @response.formats.should == []
8
+ end
9
+ end
10
+
11
+ describe Resourceful::Response, "with a few formats" do
12
+ before :each do
13
+ @response = Resourceful::Response.new
14
+ @response.html
15
+ @response.js {'javascript'}
16
+ @response.xml {'xml'}
17
+ end
18
+
19
+ it "should store the formats and blocks" do
20
+ @response.formats.should have_any {|f,p| f == :js && p.call == 'javascript'}
21
+ @response.formats.should have_any {|f,p| f == :xml && p.call == 'xml'}
22
+ end
23
+
24
+ it "should give formats without a block an empty block" do
25
+ @response.formats.should have_any {|f,p| f == :html && Proc === p && p.call.nil?}
26
+ end
27
+
28
+ it "shouldn't allow duplicate formats" do
29
+ @response.js {'not javascript'}
30
+ @response.formats.should have_any {|f,p| f == :js && p.call == 'javascript'}
31
+ @response.formats.should_not have_any {|f,p| f == :js && p.call == 'not javascript'}
32
+ end
33
+
34
+ it "should keep the formats in sorted order" do
35
+ @response.formats.map(&:first).should == [:html, :js, :xml]
36
+ end
37
+ end
@@ -0,0 +1,314 @@
1
+ require File.dirname(__FILE__) + '/spec_helper'
2
+
3
+ describe 'Resourceful::Default::Responses', " with a _flash parameter for :error" do
4
+ include ControllerMocks
5
+ before :each do
6
+ mock_controller Resourceful::Default::Responses
7
+ @flash = {}
8
+ @controller.stubs(:flash).returns(@flash)
9
+ @params = {:_flash => {:error => 'Oh no, an error!'}}
10
+ @controller.stubs(:params).returns(@params)
11
+ end
12
+
13
+ it "should set the flash for :error to the parameter's value when set_default_flash is called on :error" do
14
+ @controller.set_default_flash(:error, "Aw there's no error!")
15
+ @flash[:error].should == 'Oh no, an error!'
16
+ end
17
+
18
+ it "should set the flash for :message to the default value when set_default_flash is called on :message" do
19
+ @controller.set_default_flash(:message, "All jim dandy!")
20
+ @flash[:message].should == 'All jim dandy!'
21
+ end
22
+
23
+ it "shouldn't set the flash for :error when set_default_flash is called on :message" do
24
+ @controller.set_default_flash(:message, "All jim dandy!")
25
+ @flash[:error].should be_nil
26
+ end
27
+ end
28
+
29
+ describe 'Resourceful::Default::Responses', " with a _redirect parameter on :failure" do
30
+ include ControllerMocks
31
+ before :each do
32
+ mock_controller Resourceful::Default::Responses
33
+ @params = {:_redirect_on => {:failure => 'http://hamptoncatlin.com/'}}
34
+ @controller.stubs(:params).returns(@params)
35
+ end
36
+
37
+ it "should set the redirect for :failure to the parameter's value when set_default_redirect is called on :failure" do
38
+ @controller.expects(:redirect_to).with('http://hamptoncatlin.com/')
39
+ @controller.set_default_redirect(:back, :status => :failure)
40
+ end
41
+
42
+ it "should set the redirect for :success to the default value when set_default_redirect is called on :success" do
43
+ @controller.expects(:redirect_to).with(:back)
44
+ @controller.set_default_redirect(:back, :status => :success)
45
+ end
46
+
47
+ it "shouldn't set the redirect for :failure when set_default_redirect is called on :success" do
48
+ @controller.expects(:redirect_to).with(:back)
49
+ @controller.expects(:redirect_to).with('http://hamptoncatlin.com/').never
50
+ @controller.set_default_redirect(:back, :status => :success)
51
+ end
52
+
53
+ it "should set the default redirect for :success by default" do
54
+ @controller.expects(:redirect_to).with(:back)
55
+ @controller.set_default_redirect(:back)
56
+ end
57
+ end
58
+
59
+ describe 'Resourceful::Default::Responses', ' for show' do
60
+ include ControllerMocks
61
+ before :each do
62
+ mock_kontroller
63
+ create_builder
64
+ made_resourceful(Resourceful::Default::Responses)
65
+ @builder.apply
66
+ end
67
+
68
+ it "should have an empty HTML response" do
69
+ responses[:show].find { |f, p| f == :html }[1].call.should == nil
70
+ end
71
+
72
+ it "should have an empty JS response" do
73
+ responses[:show].find { |f, p| f == :js }[1].call.should == nil
74
+ end
75
+ end
76
+
77
+ describe 'Resourceful::Default::Responses', ' for index' do
78
+ include ControllerMocks
79
+ before :each do
80
+ mock_kontroller
81
+ create_builder
82
+ made_resourceful(Resourceful::Default::Responses)
83
+ @builder.apply
84
+ end
85
+
86
+ it "should have an empty HTML response" do
87
+ responses[:index].find { |f, p| f == :html }[1].call.should == nil
88
+ end
89
+
90
+ it "should have an empty JS response" do
91
+ responses[:index].find { |f, p| f == :js }[1].call.should == nil
92
+ end
93
+ end
94
+
95
+ describe 'Resourceful::Default::Responses', ' for edit' do
96
+ include ControllerMocks
97
+ before :each do
98
+ mock_kontroller
99
+ create_builder
100
+ made_resourceful(Resourceful::Default::Responses)
101
+ @builder.apply
102
+ end
103
+
104
+ it "should have an empty HTML response" do
105
+ responses[:edit].find { |f, p| f == :html }[1].call.should == nil
106
+ end
107
+
108
+ it "should have an empty JS response" do
109
+ responses[:edit].find { |f, p| f == :js }[1].call.should == nil
110
+ end
111
+ end
112
+
113
+ describe 'Resourceful::Default::Responses', ' for new' do
114
+ include ControllerMocks
115
+ before :each do
116
+ mock_kontroller
117
+ create_builder
118
+ made_resourceful(Resourceful::Default::Responses)
119
+ @builder.apply
120
+ end
121
+
122
+ it "should have an empty HTML response" do
123
+ responses[:new].find { |f, p| f == :html }[1].call.should == nil
124
+ end
125
+
126
+ it "should have an empty JS response" do
127
+ responses[:new].find { |f, p| f == :js }[1].call.should == nil
128
+ end
129
+ end
130
+
131
+ describe 'Resourceful::Default::Responses', ' for show_fails' do
132
+ include ControllerMocks
133
+ before :each do
134
+ mock_controller Resourceful::Default::Callbacks
135
+ create_builder
136
+ made_resourceful(Resourceful::Default::Responses)
137
+ @builder.apply
138
+ end
139
+
140
+ it "should give a 404 error for HTML" do
141
+ @controller.expects(:render).with(:text => "No item found", :status => 404)
142
+ @controller.scope(responses[:show_fails].find { |f, p| f == :html }[1]).call
143
+ end
144
+
145
+ it "should give a 404 error for JS" do
146
+ @controller.expects(:render).with(:text => "No item found", :status => 404)
147
+ @controller.scope(responses[:show_fails].find { |f, p| f == :js }[1]).call
148
+ end
149
+
150
+ it "should give a 404 error for XML" do
151
+ @controller.expects(:render).with(:text => "No item found", :status => 404)
152
+ @controller.scope(responses[:show_fails].find { |f, p| f == :xml }[1]).call
153
+ end
154
+ end
155
+
156
+ describe 'Resourceful::Default::Responses', ' for create' do
157
+ include ControllerMocks
158
+ before :each do
159
+ mock_controller Resourceful::Default::Callbacks
160
+ create_builder
161
+ made_resourceful(Resourceful::Default::Responses)
162
+ @builder.apply
163
+
164
+ [:set_default_flash, :set_default_redirect, :object_path].each(&@controller.method(:stubs))
165
+ end
166
+
167
+ it "should have an empty JS response" do
168
+ responses[:create].find { |f, p| f == :js }[1].call.should == nil
169
+ end
170
+
171
+ it "should flash a success message to :notice by default for HTML" do
172
+ @controller.expects(:set_default_flash).with(:notice, "Create successful!")
173
+ @controller.scope(responses[:create].find { |f, p| f == :html }[1]).call
174
+ end
175
+
176
+ it "should redirect to object_path by default for HTML" do
177
+ @controller.stubs(:object_path).returns("/posts/12")
178
+ @controller.expects(:set_default_redirect).with("/posts/12")
179
+ @controller.scope(responses[:create].find { |f, p| f == :html }[1]).call
180
+ end
181
+ end
182
+
183
+ describe 'Resourceful::Default::Responses', ' for create_fails' do
184
+ include ControllerMocks
185
+ before :each do
186
+ mock_controller Resourceful::Default::Callbacks
187
+ create_builder
188
+ made_resourceful(Resourceful::Default::Responses)
189
+ @builder.apply
190
+
191
+ [:set_default_flash, :render].each(&@controller.method(:stubs))
192
+ end
193
+
194
+ it "should have an empty JS response" do
195
+ responses[:create_fails].find { |f, p| f == :js }[1].call.should == nil
196
+ end
197
+
198
+ it "should flash a failure message to :error by default for HTML" do
199
+ @controller.expects(:set_default_flash).with(:error, "There was a problem!")
200
+ @controller.scope(responses[:create_fails].find { |f, p| f == :html }[1]).call
201
+ end
202
+
203
+ it "should render new with a 422 error for HTML" do
204
+ @controller.expects(:render).with(:action => :new, :status => 422)
205
+ @controller.scope(responses[:create_fails].find { |f, p| f == :html }[1]).call
206
+ end
207
+ end
208
+
209
+ describe 'Resourceful::Default::Responses', ' for update' do
210
+ include ControllerMocks
211
+ before :each do
212
+ mock_controller Resourceful::Default::Callbacks
213
+ create_builder
214
+ made_resourceful(Resourceful::Default::Responses)
215
+ @builder.apply
216
+
217
+ [:set_default_flash, :set_default_redirect, :object_path].each(&@controller.method(:stubs))
218
+ end
219
+
220
+ it "should have an empty JS response" do
221
+ responses[:update].find { |f, p| f == :js }[1].call.should == nil
222
+ end
223
+
224
+ it "should flash a success message to :notice by default for HTML" do
225
+ @controller.expects(:set_default_flash).with(:notice, "Save successful!")
226
+ @controller.scope(responses[:update].find { |f, p| f == :html }[1]).call
227
+ end
228
+
229
+ it "should redirect to object_path by default for HTML" do
230
+ @controller.stubs(:object_path).returns("/posts/12")
231
+ @controller.expects(:set_default_redirect).with("/posts/12")
232
+ @controller.scope(responses[:update].find { |f, p| f == :html }[1]).call
233
+ end
234
+ end
235
+
236
+ describe 'Resourceful::Default::Responses', ' for update_fails' do
237
+ include ControllerMocks
238
+ before :each do
239
+ mock_controller Resourceful::Default::Callbacks
240
+ create_builder
241
+ made_resourceful(Resourceful::Default::Responses)
242
+ @builder.apply
243
+
244
+ [:set_default_flash, :render].each(&@controller.method(:stubs))
245
+ end
246
+
247
+ it "should have an empty JS response" do
248
+ responses[:update_fails].find { |f, p| f == :js }[1].call.should == nil
249
+ end
250
+
251
+ it "should flash a failure message to :error by default for HTML" do
252
+ @controller.expects(:set_default_flash).with(:error, "There was a problem saving!")
253
+ @controller.scope(responses[:update_fails].find { |f, p| f == :html }[1]).call
254
+ end
255
+
256
+ it "should render edit with a 422 error for HTML" do
257
+ @controller.expects(:render).with(:action => :edit, :status => 422)
258
+ @controller.scope(responses[:update_fails].find { |f, p| f == :html }[1]).call
259
+ end
260
+ end
261
+
262
+
263
+ describe 'Resourceful::Default::Responses', ' for destroy' do
264
+ include ControllerMocks
265
+ before :each do
266
+ mock_controller Resourceful::Default::Callbacks
267
+ create_builder
268
+ made_resourceful(Resourceful::Default::Responses)
269
+ @builder.apply
270
+
271
+ [:set_default_flash, :set_default_redirect, :objects_path].each(&@controller.method(:stubs))
272
+ end
273
+
274
+ it "should have an empty JS response" do
275
+ responses[:destroy].find { |f, p| f == :js }[1].call.should == nil
276
+ end
277
+
278
+ it "should flash a success message to :notice by default for HTML" do
279
+ @controller.expects(:set_default_flash).with(:notice, "Record deleted!")
280
+ @controller.scope(responses[:destroy].find { |f, p| f == :html }[1]).call
281
+ end
282
+
283
+ it "should redirect to objects_path by default for HTML" do
284
+ @controller.stubs(:objects_path).returns("/posts")
285
+ @controller.expects(:set_default_redirect).with("/posts")
286
+ @controller.scope(responses[:destroy].find { |f, p| f == :html }[1]).call
287
+ end
288
+ end
289
+
290
+ describe 'Resourceful::Default::Responses', ' for destroy_fails' do
291
+ include ControllerMocks
292
+ before :each do
293
+ mock_controller Resourceful::Default::Callbacks
294
+ create_builder
295
+ made_resourceful(Resourceful::Default::Responses)
296
+ @builder.apply
297
+
298
+ [:set_default_flash, :set_default_redirect, :render].each(&@controller.method(:stubs))
299
+ end
300
+
301
+ it "should have an empty JS response" do
302
+ responses[:destroy_fails].find { |f, p| f == :js }[1].call.should == nil
303
+ end
304
+
305
+ it "should flash a failure message to :error by default for HTML" do
306
+ @controller.expects(:set_default_flash).with(:error, "There was a problem deleting!")
307
+ @controller.scope(responses[:destroy_fails].find { |f, p| f == :html }[1]).call
308
+ end
309
+
310
+ it "should redirect back on failure by default for HTML" do
311
+ @controller.expects(:set_default_redirect).with(:back, :status => :failure)
312
+ @controller.scope(responses[:destroy_fails].find { |f, p| f == :html }[1]).call
313
+ end
314
+ end
@@ -0,0 +1,133 @@
1
+ require File.dirname(__FILE__) + '/spec_helper'
2
+
3
+ describe Resourceful::Serialize, ".normalize_attributes" do
4
+ it "should return nil if given nil" do
5
+ Resourceful::Serialize.normalize_attributes(nil).should be_nil
6
+ end
7
+
8
+ it "should return a basic hash if given a non-injectable attribute" do
9
+ Resourceful::Serialize.normalize_attributes(:foo).should == {:foo => nil}
10
+ Resourceful::Serialize.normalize_attributes(12).should == {12 => nil}
11
+ end
12
+
13
+ it "should return a basic hash with a symbol key if given a string attribute" do
14
+ Resourceful::Serialize.normalize_attributes("foo").should == {:foo => nil}
15
+ end
16
+
17
+ it "should preserve hashes" do
18
+ Resourceful::Serialize.normalize_attributes({:foo => nil, :bar => nil, :baz => nil}).should ==
19
+ {:foo => nil, :bar => nil, :baz => nil}
20
+ Resourceful::Serialize.normalize_attributes({:foo => 3, :bar => 1, :baz => 4}).should ==
21
+ {:foo => 3, :bar => 1, :baz => 4}
22
+ Resourceful::Serialize.normalize_attributes({:foo => 3, :bar => 1, :baz => [:foo, :bar]}).should ==
23
+ {:foo => 3, :bar => 1, :baz => [:foo, :bar]}
24
+ end
25
+
26
+ it "should merge injectable attributes into one big hash" do
27
+ Resourceful::Serialize.normalize_attributes([:foo, :bar, :baz]).should ==
28
+ {:foo => nil, :bar => nil, :baz => nil}
29
+ Resourceful::Serialize.normalize_attributes([:foo, :bar, {:baz => nil},
30
+ :boom, {:bop => nil, :blat => nil}]).should ==
31
+ {:foo => nil, :bar => nil, :baz => nil, :boom => nil, :bop => nil, :blat => nil}
32
+ Resourceful::Serialize.normalize_attributes([:foo, :bar, {:baz => 12},
33
+ :boom, {:bop => "foo", :blat => [:fee, :fi, :fo]}]).should ==
34
+ {:foo => nil, :bar => nil, :baz => 12, :boom => nil, :bop => "foo", :blat => [:fee, :fi, :fo]}
35
+ end
36
+ end
37
+
38
+ describe Array, " of non-serializable objects" do
39
+ before :each do
40
+ @array = [1, 2, 3, 4, "foo"]
41
+ end
42
+
43
+ it "should return itself for #to_serializable" do
44
+ @array.to_serializable(nil).should == @array
45
+ end
46
+
47
+ it "should raise an error for #serialize" do
48
+ lambda { @array.serialize(:yaml, :attributes => [:foo]) }.should raise_error("Not all elements respond to to_serializable")
49
+ end
50
+ end
51
+
52
+ describe Array, " of serializable objects" do
53
+ before :each do
54
+ @cat = stub_model("Cat")
55
+ @dog = stub_model("Dog")
56
+ @array = %w{brown yellow green}.zip(%w{rex rover fido}).
57
+ map { |c, d| @cat.new(:fur => c, :friend => @dog.new(:name => d)) }
58
+ end
59
+
60
+ it "should return an array of serializable hashes for #to_serializable" do
61
+ @array.to_serializable([:fur]).should == [{'fur' => 'brown'}, {'fur' => 'yellow'}, {'fur' => 'green'}]
62
+ end
63
+
64
+ it "should follow deep attributes for #to_serializable" do
65
+ @array.to_serializable([:fur, {:friend => :name}]).should ==
66
+ [{'fur' => 'brown', 'friend' => {'name' => 'rex'}},
67
+ {'fur' => 'yellow', 'friend' => {'name' => 'rover'}},
68
+ {'fur' => 'green', 'friend' => {'name' => 'fido'}}]
69
+ end
70
+
71
+ it "should raise an error if #serialize is called without the :attributes option" do
72
+ lambda { @array.serialize(:yaml, {}) }.should raise_error("Must specify :attributes option")
73
+ end
74
+
75
+ it "should serialize to a hash with a pluralized root for #serialize" do
76
+ YAML.load(@array.serialize(:yaml, :attributes => [:fur, {:friend => :name}])).should ==
77
+ {"cats" => [{'fur' => 'brown', 'friend' => {'name' => 'rex'}},
78
+ {'fur' => 'yellow', 'friend' => {'name' => 'rover'}},
79
+ {'fur' => 'green', 'friend' => {'name' => 'fido'}}]}
80
+ end
81
+
82
+ it "should serialize to an XML document with a pluralized root for #serialize(:xml, ...)" do
83
+ doc = REXML::Document.new(@array.serialize(:xml, :attributes => [:fur, {:friend => :name}]),
84
+ :ignore_whitespace_nodes => :all)
85
+ doc.root.name.should == "cats"
86
+ cats = doc.get_elements('/cats/cat')
87
+ cats.size.should == 3
88
+ cats.zip(%w{brown yellow green}, %w{rex rover fido}) do |cat, fur, dog|
89
+ cat.children.find { |e| e.name == "fur" }.text.should == fur
90
+ cat.children.find { |e| e.name == "friend" }.children[0].text.should == dog
91
+ end
92
+ end
93
+ end
94
+
95
+ describe ActiveRecord::Base, " with a few attributes and an association" do
96
+ before :each do
97
+ @person = stub_model("Person")
98
+ @party_hat = stub_model("PartyHat")
99
+ @model = @person.new(:name => "joe", :eye_color => "blue", :hairs => 567,
100
+ :party_hat => @party_hat.new(:color => 'blue', :size => 12, :pattern => 'stripey'))
101
+ end
102
+
103
+ it "should raise an error if #to_serializable is called without attributes" do
104
+ lambda { @model.to_serializable(nil) }.should raise_error("Must specify attributes for #<Person>.to_serializable")
105
+ end
106
+
107
+ it "should return an attributes hash for #to_serializable" do
108
+ @model.to_serializable([:name, :hairs, {:party_hat => [:color, :size]}]).should ==
109
+ {'name' => 'joe', 'hairs' => 567, 'party_hat' => {
110
+ 'color' => 'blue', 'size' => 12
111
+ }}
112
+ end
113
+
114
+ it "should raise an error if #serialize is called without the :attributes option" do
115
+ lambda { @model.serialize(:yaml, {}) }.should raise_error("Must specify :attributes option")
116
+ end
117
+
118
+ it "should serialize to a hash for #serialize" do
119
+ YAML.load(@model.serialize(:yaml, :attributes => [:hairs, :eye_color, {:party_hat => :size}])).should ==
120
+ {"person" => {'hairs' => 567, 'eye_color' => 'blue', 'party_hat' => {'size' => 12}}}
121
+ end
122
+
123
+ it "should serialize to an XML document for #serialize(:xml, ...)" do
124
+ doc = REXML::Document.new(@model.serialize(:xml, :attributes => [:name, :eye_color, {:party_hat => :pattern}]),
125
+ :ignore_whitespace_nodes => :all)
126
+ doc.root.name.should == "person"
127
+ doc.root.children.find { |e| e.name == "name" }.text.should == "joe"
128
+ doc.root.children.find { |e| e.name == "eye-color" }.text.should == "blue"
129
+
130
+ hat = doc.root.children.find { |e| e.name == "party-hat" }
131
+ hat.children.find { |e| e.name == "pattern" }.text.should == "stripey"
132
+ end
133
+ end