mongo_mapper 0.12.0 → 0.13.0.beta1

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 (154) hide show
  1. checksums.yaml +7 -0
  2. data/README.rdoc +35 -13
  3. data/bin/mmconsole +1 -1
  4. data/lib/mongo_mapper.rb +4 -0
  5. data/lib/mongo_mapper/connection.rb +17 -6
  6. data/lib/mongo_mapper/document.rb +1 -0
  7. data/lib/mongo_mapper/exceptions.rb +4 -1
  8. data/lib/mongo_mapper/extensions/binary.rb +1 -1
  9. data/lib/mongo_mapper/extensions/boolean.rb +20 -23
  10. data/lib/mongo_mapper/extensions/date.rb +3 -3
  11. data/lib/mongo_mapper/extensions/integer.rb +5 -1
  12. data/lib/mongo_mapper/extensions/kernel.rb +2 -0
  13. data/lib/mongo_mapper/extensions/ordered_hash.rb +23 -0
  14. data/lib/mongo_mapper/extensions/string.rb +2 -2
  15. data/lib/mongo_mapper/extensions/time.rb +7 -5
  16. data/lib/mongo_mapper/middleware/identity_map.rb +3 -4
  17. data/lib/mongo_mapper/plugins.rb +1 -1
  18. data/lib/mongo_mapper/plugins/associations.rb +11 -5
  19. data/lib/mongo_mapper/plugins/associations/base.rb +5 -3
  20. data/lib/mongo_mapper/plugins/associations/belongs_to_polymorphic_proxy.rb +0 -0
  21. data/lib/mongo_mapper/plugins/associations/belongs_to_proxy.rb +8 -8
  22. data/lib/mongo_mapper/plugins/associations/collection.rb +2 -0
  23. data/lib/mongo_mapper/plugins/associations/many_documents_proxy.rb +32 -7
  24. data/lib/mongo_mapper/plugins/associations/many_embedded_proxy.rb +2 -2
  25. data/lib/mongo_mapper/plugins/associations/one_proxy.rb +12 -12
  26. data/lib/mongo_mapper/plugins/associations/proxy.rb +5 -1
  27. data/lib/mongo_mapper/plugins/associations/single_association.rb +6 -6
  28. data/lib/mongo_mapper/plugins/clone.rb +4 -2
  29. data/lib/mongo_mapper/plugins/dirty.rb +22 -21
  30. data/lib/mongo_mapper/plugins/document.rb +4 -4
  31. data/lib/mongo_mapper/plugins/dumpable.rb +22 -0
  32. data/lib/mongo_mapper/plugins/embedded_callbacks.rb +58 -9
  33. data/lib/mongo_mapper/plugins/identity_map.rb +42 -32
  34. data/lib/mongo_mapper/plugins/keys.rb +133 -54
  35. data/lib/mongo_mapper/plugins/keys/key.rb +68 -22
  36. data/lib/mongo_mapper/plugins/modifiers.rb +26 -19
  37. data/lib/mongo_mapper/plugins/persistence.rb +15 -5
  38. data/lib/mongo_mapper/plugins/querying.rb +15 -40
  39. data/lib/mongo_mapper/plugins/querying/{decorator.rb → decorated_plucky_query.rb} +24 -4
  40. data/lib/mongo_mapper/plugins/rails.rb +22 -2
  41. data/lib/mongo_mapper/plugins/safe.rb +8 -5
  42. data/lib/mongo_mapper/plugins/sci.rb +26 -4
  43. data/lib/mongo_mapper/plugins/scopes.rb +5 -4
  44. data/lib/mongo_mapper/plugins/timestamps.rb +11 -4
  45. data/lib/mongo_mapper/plugins/validations.rb +1 -1
  46. data/lib/mongo_mapper/utils.rb +12 -0
  47. data/lib/mongo_mapper/version.rb +1 -1
  48. data/lib/rails/generators/mongo_mapper/config/config_generator.rb +20 -7
  49. data/lib/rails/generators/mongo_mapper/config/templates/mongo.yml +6 -0
  50. data/lib/rails/generators/mongo_mapper/model/model_generator.rb +18 -1
  51. data/lib/rails/generators/mongo_mapper/model/templates/model.rb +9 -5
  52. data/{test/functional/test_accessible.rb → spec/functional/accessible_spec.rb} +29 -29
  53. data/{test/functional/associations/test_belongs_to_polymorphic_proxy.rb → spec/functional/associations/belongs_to_polymorphic_proxy_spec.rb} +10 -10
  54. data/{test/functional/associations/test_belongs_to_proxy.rb → spec/functional/associations/belongs_to_proxy_spec.rb} +82 -64
  55. data/{test/functional/associations/test_in_array_proxy.rb → spec/functional/associations/in_array_proxy_spec.rb} +68 -68
  56. data/{test/functional/associations/test_many_documents_as_proxy.rb → spec/functional/associations/many_documents_as_proxy_spec.rb} +37 -38
  57. data/{test/functional/associations/test_many_documents_proxy.rb → spec/functional/associations/many_documents_proxy_spec.rb} +233 -146
  58. data/{test/functional/associations/test_many_embedded_polymorphic_proxy.rb → spec/functional/associations/many_embedded_polymorphic_proxy_spec.rb} +19 -20
  59. data/{test/functional/associations/test_many_embedded_proxy.rb → spec/functional/associations/many_embedded_proxy_spec.rb} +23 -24
  60. data/{test/functional/associations/test_many_polymorphic_proxy.rb → spec/functional/associations/many_polymorphic_proxy_spec.rb} +45 -46
  61. data/{test/functional/associations/test_one_as_proxy.rb → spec/functional/associations/one_as_proxy_spec.rb} +75 -77
  62. data/{test/functional/associations/test_one_embedded_polymorphic_proxy.rb → spec/functional/associations/one_embedded_polymorphic_proxy_spec.rb} +31 -32
  63. data/{test/functional/associations/test_one_embedded_proxy.rb → spec/functional/associations/one_embedded_proxy_spec.rb} +10 -10
  64. data/{test/functional/associations/test_one_proxy.rb → spec/functional/associations/one_proxy_spec.rb} +125 -102
  65. data/spec/functional/associations_spec.rb +48 -0
  66. data/{test/functional/test_binary.rb → spec/functional/binary_spec.rb} +6 -6
  67. data/spec/functional/caching_spec.rb +75 -0
  68. data/{test/functional/test_callbacks.rb → spec/functional/callbacks_spec.rb} +84 -26
  69. data/{test/functional/test_dirty.rb → spec/functional/dirty_spec.rb} +57 -42
  70. data/{test/functional/test_document.rb → spec/functional/document_spec.rb} +52 -52
  71. data/spec/functional/dumpable_spec.rb +24 -0
  72. data/{test/functional/test_dynamic_querying.rb → spec/functional/dynamic_querying_spec.rb} +14 -14
  73. data/{test/functional/test_embedded_document.rb → spec/functional/embedded_document_spec.rb} +51 -42
  74. data/{test/functional/test_equality.rb → spec/functional/equality_spec.rb} +4 -4
  75. data/spec/functional/extensions_spec.rb +16 -0
  76. data/{test/functional/test_identity_map.rb → spec/functional/identity_map_spec.rb} +73 -61
  77. data/spec/functional/indexes_spec.rb +48 -0
  78. data/spec/functional/keys_spec.rb +224 -0
  79. data/{test/functional/test_logger.rb → spec/functional/logger_spec.rb} +6 -6
  80. data/spec/functional/modifiers_spec.rb +550 -0
  81. data/spec/functional/pagination_spec.rb +89 -0
  82. data/spec/functional/protected_spec.rb +199 -0
  83. data/spec/functional/querying_spec.rb +1003 -0
  84. data/spec/functional/rails_spec.rb +55 -0
  85. data/spec/functional/safe_spec.rb +163 -0
  86. data/{test/functional/test_sci.rb → spec/functional/sci_spec.rb} +123 -34
  87. data/{test/functional/test_scopes.rb → spec/functional/scopes_spec.rb} +59 -26
  88. data/spec/functional/timestamps_spec.rb +97 -0
  89. data/{test/functional/test_touch.rb → spec/functional/touch_spec.rb} +13 -13
  90. data/spec/functional/userstamps_spec.rb +46 -0
  91. data/{test/functional/test_validations.rb → spec/functional/validations_spec.rb} +64 -64
  92. data/spec/spec_helper.rb +81 -0
  93. data/spec/support/matchers.rb +24 -0
  94. data/{test → spec/support}/models.rb +1 -6
  95. data/spec/unit/associations/base_spec.rb +146 -0
  96. data/spec/unit/associations/belongs_to_association_spec.rb +30 -0
  97. data/spec/unit/associations/many_association_spec.rb +64 -0
  98. data/spec/unit/associations/one_association_spec.rb +48 -0
  99. data/{test/unit/associations/test_proxy.rb → spec/unit/associations/proxy_spec.rb} +21 -21
  100. data/{test/unit/test_clone.rb → spec/unit/clone_spec.rb} +21 -11
  101. data/spec/unit/config_generator_spec.rb +24 -0
  102. data/{test/unit/test_document.rb → spec/unit/document_spec.rb} +42 -42
  103. data/{test/unit/test_dynamic_finder.rb → spec/unit/dynamic_finder_spec.rb} +28 -28
  104. data/{test/unit/test_embedded_document.rb → spec/unit/embedded_document_spec.rb} +102 -108
  105. data/{test/unit/test_equality.rb → spec/unit/equality_spec.rb} +7 -7
  106. data/{test/unit/test_exceptions.rb → spec/unit/exceptions_spec.rb} +3 -3
  107. data/{test/unit/test_extensions.rb → spec/unit/extensions_spec.rb} +85 -71
  108. data/spec/unit/identity_map_middleware_spec.rb +134 -0
  109. data/{test/unit/test_inspect.rb → spec/unit/inspect_spec.rb} +8 -8
  110. data/{test/unit/test_key.rb → spec/unit/key_spec.rb} +82 -52
  111. data/spec/unit/keys_spec.rb +155 -0
  112. data/spec/unit/model_generator_spec.rb +47 -0
  113. data/spec/unit/mongo_mapper_spec.rb +184 -0
  114. data/spec/unit/pagination_spec.rb +11 -0
  115. data/{test/unit/test_plugins.rb → spec/unit/plugins_spec.rb} +14 -14
  116. data/spec/unit/rails_compatibility_spec.rb +40 -0
  117. data/{test/unit/test_rails_reflect_on_association.rb → spec/unit/rails_reflect_on_association_spec.rb} +9 -9
  118. data/{test/unit/test_rails.rb → spec/unit/rails_spec.rb} +31 -31
  119. data/spec/unit/serialization_spec.rb +169 -0
  120. data/spec/unit/serializers/json_serializer_spec.rb +218 -0
  121. data/spec/unit/serializers/xml_serializer_spec.rb +198 -0
  122. data/{test/unit/test_time_zones.rb → spec/unit/time_zones_spec.rb} +8 -8
  123. data/{test/unit/test_translation.rb → spec/unit/translation_spec.rb} +6 -6
  124. data/{test/unit/test_validations.rb → spec/unit/validations_spec.rb} +72 -59
  125. metadata +199 -179
  126. data/test/_NOTE_ON_TESTING +0 -1
  127. data/test/functional/test_associations.rb +0 -46
  128. data/test/functional/test_caching.rb +0 -77
  129. data/test/functional/test_indexes.rb +0 -50
  130. data/test/functional/test_modifiers.rb +0 -537
  131. data/test/functional/test_pagination.rb +0 -91
  132. data/test/functional/test_protected.rb +0 -201
  133. data/test/functional/test_querying.rb +0 -935
  134. data/test/functional/test_safe.rb +0 -76
  135. data/test/functional/test_timestamps.rb +0 -62
  136. data/test/functional/test_userstamps.rb +0 -44
  137. data/test/support/railtie.rb +0 -4
  138. data/test/support/railtie/autoloaded.rb +0 -2
  139. data/test/support/railtie/not_autoloaded.rb +0 -3
  140. data/test/support/railtie/parent.rb +0 -3
  141. data/test/test_active_model_lint.rb +0 -18
  142. data/test/test_helper.rb +0 -93
  143. data/test/unit/associations/test_base.rb +0 -146
  144. data/test/unit/associations/test_belongs_to_association.rb +0 -29
  145. data/test/unit/associations/test_many_association.rb +0 -63
  146. data/test/unit/associations/test_one_association.rb +0 -47
  147. data/test/unit/serializers/test_json_serializer.rb +0 -216
  148. data/test/unit/serializers/test_xml_serializer.rb +0 -196
  149. data/test/unit/test_identity_map_middleware.rb +0 -132
  150. data/test/unit/test_keys.rb +0 -65
  151. data/test/unit/test_mongo_mapper.rb +0 -157
  152. data/test/unit/test_pagination.rb +0 -11
  153. data/test/unit/test_rails_compatibility.rb +0 -38
  154. data/test/unit/test_serialization.rb +0 -166
@@ -0,0 +1,218 @@
1
+ require 'spec_helper'
2
+
3
+ module JsonSerialization
4
+ describe "JsonSerialization" do
5
+
6
+ # Helper function in case things change in the future
7
+ # - replacing all those to_json calls was a nightmare
8
+ def convert_to_json(object, options={})
9
+ ActiveSupport::JSON.encode(object, options)
10
+ end
11
+
12
+ class Tag
13
+ include MongoMapper::EmbeddedDocument
14
+ key :name, String
15
+ end
16
+
17
+ class Contact
18
+ include MongoMapper::Document
19
+ key :name, String
20
+ key :age, Integer
21
+ key :created_at, Time
22
+ key :awesome, Boolean
23
+ key :preferences, Hash
24
+
25
+ many :tags, :class_name => 'JsonSerialization::Tag'
26
+ end
27
+
28
+ before do
29
+ Kernel.const_set('TopLevelContact', Doc('TopLevelContact'))
30
+ TopLevelContact.key :name, String
31
+
32
+ Contact.include_root_in_json = false
33
+ @contact = Contact.new(
34
+ :name => 'Konata Izumi',
35
+ :age => 16,
36
+ :created_at => Time.utc(2006, 8, 1),
37
+ :awesome => true,
38
+ :preferences => { :shows => 'anime' }
39
+ )
40
+ @top_level_contact = TopLevelContact.new(
41
+ :name => 'Konata Izumi'
42
+ )
43
+ end
44
+
45
+ after do
46
+ Kernel.send(:remove_const, 'TopLevelContact') if Object.const_defined?('TopLevelContact')
47
+ end
48
+
49
+ it "should include root for class with no module" do
50
+ TopLevelContact.include_root_in_json = true
51
+ convert_to_json(@top_level_contact).should match %r{^\{"top_level_contact":\s?\{}
52
+ end
53
+
54
+ it "should include demodulized root" do
55
+ Contact.include_root_in_json = true
56
+ convert_to_json(@contact).should match %r{^\{"contact":\s?\{}
57
+ end
58
+
59
+ it "should encode all encodable attributes" do
60
+ json = convert_to_json(@contact)
61
+
62
+ json.should_not match %r{"_id"}
63
+ json.should match %r{"name":"Konata Izumi"}
64
+ json.should match %r{"age":16}
65
+ json.should include(%("created_at":#{ActiveSupport::JSON.encode(Time.utc(2006, 8, 1))}))
66
+ json.should match %r{"awesome":true}
67
+ json.should match %r{"preferences":\{"shows":"anime"\}}
68
+ end
69
+
70
+ it "should allow attribute filtering with only" do
71
+ json = convert_to_json(@contact, :only => [:name, :age])
72
+
73
+ json.should_not match %r{"_id"}
74
+ json.should match %r{"name":"Konata Izumi"}
75
+ json.should match %r{"age":16}
76
+ json.should_not match %r{"awesome"}
77
+ json.should_not match %r{"created_at"}
78
+ json.should_not match %r{"preferences"}
79
+ end
80
+
81
+ it "should allow attribute filtering with except" do
82
+ json = convert_to_json(@contact, :except => [:name, :age])
83
+
84
+ json.should_not match %r{"_id"}
85
+ json.should_not match %r{"name"}
86
+ json.should_not match %r{"age"}
87
+ json.should match %r{"awesome"}
88
+ json.should match %r{"created_at"}
89
+ json.should match %r{"preferences"}
90
+ end
91
+
92
+ context "_id key" do
93
+ it "should not be included by default" do
94
+ json = convert_to_json(@contact)
95
+ json.should_not match %r{"_id":}
96
+ end
97
+
98
+ it "should not be included even if :except is used" do
99
+ json = convert_to_json(@contact, :except => :name)
100
+ json.should_not match %r{"_id":}
101
+ end
102
+ end
103
+
104
+ context "id method" do
105
+ before do
106
+ def @contact.label; "Has cheezburger"; end
107
+ def @contact.favorite_quote; "Constraints are liberating"; end
108
+ end
109
+
110
+ it "should be included by default" do
111
+ json = convert_to_json(@contact)
112
+ json.should match %r{"id"}
113
+ end
114
+
115
+ it "should be included when single method included" do
116
+ json = convert_to_json(@contact, :methods => :label)
117
+ json.should match %r{"id"}
118
+ json.should match %r{"label":"Has cheezburger"}
119
+ json.should match %r{"name":"Konata Izumi"}
120
+ json.should_not match %r{"favorite_quote":"Constraints are liberating"}
121
+ end
122
+
123
+ it "should be included when multiple methods included" do
124
+ json = convert_to_json(@contact, :methods => [:label, :favorite_quote])
125
+ json.should match %r{"id"}
126
+ json.should match %r{"label":"Has cheezburger"}
127
+ json.should match %r{"favorite_quote":"Constraints are liberating"}
128
+ json.should match %r{"name":"Konata Izumi"}
129
+ end
130
+
131
+ it "should not be included if :only is present" do
132
+ json = convert_to_json(@contact, :only => :name)
133
+ json.should_not match %r{"id":}
134
+ end
135
+
136
+ it "should be represented by a string" do
137
+ json = convert_to_json(@contact)
138
+ json.should match %r{"id":"}
139
+ end
140
+ end
141
+
142
+ context "including methods" do
143
+ before do
144
+ def @contact.label; "Has cheezburger"; end
145
+ def @contact.favorite_quote; "Constraints are liberating"; end
146
+ end
147
+
148
+ it "should include single method" do
149
+ json = convert_to_json(@contact, :methods => :label)
150
+ json.should match %r{"label":"Has cheezburger"}
151
+ end
152
+
153
+ it "should include multiple methods" do
154
+ json = convert_to_json(@contact, :only => :name, :methods => [:label, :favorite_quote])
155
+ json.should match %r{"label":"Has cheezburger"}
156
+ json.should match %r{"favorite_quote":"Constraints are liberating"}
157
+ json.should match %r{"name":"Konata Izumi"}
158
+ json.should_not match %r{"age":16}
159
+ json.should_not match %r{"awesome"}
160
+ json.should_not match %r{"created_at"}
161
+ json.should_not match %r{"preferences"}
162
+ end
163
+ end
164
+
165
+ context "array of records" do
166
+ before do
167
+ @contacts = [
168
+ Contact.new(:name => 'David', :age => 39),
169
+ Contact.new(:name => 'Mary', :age => 14)
170
+ ]
171
+ end
172
+
173
+ it "should allow attribute filtering with only" do
174
+ json =convert_to_json(@contacts, :only => :name)
175
+ json.should match %r{\{"name":"David"\}}
176
+ json.should match %r{\{"name":"Mary"\}}
177
+ end
178
+
179
+ it "should allow attribute filtering with except" do
180
+ json = convert_to_json(@contacts, :except => [:name, :preferences, :awesome, :created_at, :updated_at])
181
+ json.should match %r{"age":39}
182
+ json.should match %r{"age":14}
183
+ json.should_not match %r{"name":}
184
+ json.should_not match %r{"preferences":}
185
+ json.should_not match %r{"awesome":}
186
+ json.should_not match %r{"created_at":}
187
+ json.should_not match %r{"updated_at":}
188
+ end
189
+ end
190
+
191
+ it "should allow options for hash of records" do
192
+ contacts = {
193
+ 1 => Contact.new(:name => 'David', :age => 39),
194
+ 2 => Contact.new(:name => 'Mary', :age => 14)
195
+ }
196
+ json = convert_to_json(contacts, :only => [1, :name])
197
+ json.should match %r{"1":}
198
+ json.should match %r{\{"name":"David"\}}
199
+ json.should_not match %r{"2":}
200
+ end
201
+
202
+ it "should include embedded attributes" do
203
+ contact = Contact.new(:name => 'John', :age => 27)
204
+ contact.tags = [Tag.new(:name => 'awesome'), Tag.new(:name => 'ruby')]
205
+ json = convert_to_json(contact)
206
+ json.should match %r{"tags":}
207
+ json.should match %r{"name":"awesome"}
208
+ json.should match %r{"name":"ruby"}
209
+ end
210
+
211
+ it "should include dynamic attributes" do
212
+ contact = Contact.new(:name => 'John', :age => 27, :foo => 'bar')
213
+ contact['smell'] = 'stinky'
214
+ json = convert_to_json(contact)
215
+ json.should match %r{"smell":"stinky"}
216
+ end
217
+ end
218
+ end
@@ -0,0 +1,198 @@
1
+ require 'spec_helper'
2
+
3
+ module XmlSerialization
4
+ describe "XmlSerialization" do
5
+ class Tag
6
+ include MongoMapper::EmbeddedDocument
7
+ key :name, String
8
+ end
9
+
10
+ class Contact
11
+ include MongoMapper::Document
12
+ key :name, String
13
+ key :age, Integer
14
+ key :created_at, Time
15
+ key :awesome, Boolean
16
+ key :preferences, Hash
17
+
18
+ many :tags, :class_name => 'XmlSerialization::Tag'
19
+ end
20
+
21
+ before do
22
+ Kernel.const_set('TopLevelContact', Doc('TopLevelContact'))
23
+ TopLevelContact.key :name, String
24
+
25
+ Contact.include_root_in_json = false
26
+ @contact = Contact.new(
27
+ :name => 'Konata Izumi',
28
+ :age => 16,
29
+ :created_at => Time.utc(2006, 8, 1),
30
+ :awesome => true,
31
+ :preferences => { :shows => 'anime' }
32
+ )
33
+ @top_level_contact = TopLevelContact.new(
34
+ :name => 'Konata Izumi'
35
+ )
36
+ end
37
+
38
+ after do
39
+ Kernel.send(:remove_const, 'TopLevelContact') if Object.const_defined?('TopLevelContact')
40
+ end
41
+
42
+ it "should include root for class with no module" do
43
+ @top_level_contact.to_xml.should match %r{<top-level-contact>}
44
+ end
45
+
46
+ it "should include demodulized root" do
47
+ @contact.to_xml.should match %r{<contact>}
48
+ end
49
+
50
+ it "should encode all encodable attributes" do
51
+ xml = @contact.to_xml
52
+
53
+ xml.should_not match %r{_id}
54
+ xml.should match %r{<id>#{@contact.id}</id>}
55
+ xml.should match %r{<name>Konata Izumi</name>}
56
+ xml.should match %r{<age.*>16</age>}
57
+ xml.should match %r(<created-at type="date[tT]ime">)
58
+ xml.should match %r{<awesome type="boolean">true</awesome>}
59
+ xml.should match %r{<preferences>}
60
+ xml.should match %r{<shows>anime</shows>}
61
+ end
62
+
63
+ it "should allow attribute filtering with only" do
64
+ xml = @contact.to_xml(:only => [:name, :age])
65
+
66
+ xml.should match %r{<name>Konata Izumi</name>}
67
+ xml.should match %r{<age type="integer">16</age>}
68
+ xml.should_not match %r{<id>}
69
+ xml.should_not match %r{awesome}
70
+ xml.should_not match %r{created-at}
71
+ xml.should_not match %r{preferences}
72
+ end
73
+
74
+ it "should allow attribute filtering with except" do
75
+ xml = @contact.to_xml(:except => [:name, :age])
76
+
77
+ xml.should_not match %r{<name>Konata Izumi</name>}
78
+ xml.should_not match %r{<age type="integer">16</age>}
79
+ xml.should match %r{<id>}
80
+ xml.should match %r{awesome}
81
+ xml.should match %r{created-at}
82
+ xml.should match %r{preferences}
83
+ end
84
+
85
+ context "_id key" do
86
+ it "should not be included by default" do
87
+ @contact.to_xml.should_not match %r{_id}
88
+ end
89
+
90
+ it "should not be included even if :except is used" do
91
+ @contact.to_xml(:except => :name).should_not match %r{_id}
92
+ end
93
+ end
94
+
95
+ context "id method" do
96
+ before do
97
+ def @contact.label; "Has cheezburger"; end
98
+ def @contact.favorite_quote; "Constraints are liberating"; end
99
+ end
100
+
101
+ it "should be included by default" do
102
+ @contact.to_xml.should match %r{<id>#{@contact.id}</id>}
103
+ end
104
+
105
+ it "should be included when single method included" do
106
+ xml = @contact.to_xml(:methods => :label)
107
+ xml.should match %r{<id>}
108
+ xml.should match %r{<label>Has cheezburger</label>}
109
+ xml.should match %r{<name>Konata Izumi</name>}
110
+ xml.should_not match %r{favorite_quote}
111
+ end
112
+
113
+ it "should be included when multiple methods included" do
114
+ xml = @contact.to_xml(:methods => [:label, :favorite_quote])
115
+ xml.should match %r{<id>}
116
+ xml.should match %r{<label>Has cheezburger</label>}
117
+ xml.should match %r{<name>Konata Izumi</name>}
118
+ xml.should match %r{<favorite-quote>Constraints are liberating</favorite-quote>}
119
+ end
120
+
121
+ it "should not be included if :only is present" do
122
+ @contact.to_xml(:only => :name).should_not match %r{<id}
123
+ end
124
+
125
+ it "should be represented by a string" do
126
+ @contact.to_xml.should match %r{<id>}
127
+ end
128
+ end
129
+
130
+ context "including methods" do
131
+ before do
132
+ def @contact.label; "Has cheezburger"; end
133
+ def @contact.favorite_quote; "Constraints are liberating"; end
134
+ end
135
+
136
+ it "should include single method" do
137
+ @contact.to_xml(:methods => :label).should match %r{<label>Has cheezburger</label>}
138
+ end
139
+
140
+ it "should include multiple methods" do
141
+ xml = @contact.to_xml(:only => :name, :methods => [:label, :favorite_quote])
142
+ xml.should match %r{<label>Has cheezburger</label>}
143
+ xml.should match %r{<favorite-quote>Constraints are liberating</favorite-quote>}
144
+ xml.should match %r{<name>Konata Izumi</name>}
145
+ xml.should_not match %r{age}
146
+ xml.should_not match %r{awesome}
147
+ xml.should_not match %r{created-at}
148
+ xml.should_not match %r{preferences}
149
+
150
+ # Assert only one tag is created
151
+ xml.scan(/favorite-quote/).size.should == 2
152
+ end
153
+ end
154
+
155
+ context "array of records" do
156
+ before do
157
+ @contacts = [
158
+ Contact.new(:name => 'David', :age => 39),
159
+ Contact.new(:name => 'Mary', :age => 14)
160
+ ]
161
+ end
162
+
163
+ it "should allow attribute filtering with only" do
164
+ xml = @contacts.to_xml(:only => :name)
165
+ xml.should match %r{<name>David</name>}
166
+ xml.should match %r{<name>Mary</name>}
167
+ end
168
+
169
+ it "should allow attribute filtering with except" do
170
+ xml = @contacts.to_xml(:except => [:name, :preferences, :awesome, :created_at, :updated_at])
171
+ xml.should match %r{<age type="integer">14</age>}
172
+ xml.should match %r{<age type="integer">39</age>}
173
+ xml.should_not match %r{name}
174
+ xml.should_not match %r{preferences}
175
+ xml.should_not match %r{awesome}
176
+ xml.should_not match %r{created-at}
177
+ xml.should_not match %r{updated-at}
178
+ end
179
+ end
180
+
181
+ it "should include embedded attributes" do
182
+ contact = Contact.new(:name => 'John', :age => 27)
183
+ contact.tags = [Tag.new(:name => 'awesome'), Tag.new(:name => 'ruby')]
184
+ xml = contact.to_xml
185
+ xml.should match %r{<tags type="array">}
186
+ xml.should match %r{<id>#{contact.tags[0].id}</id>}
187
+ xml.should match %r{<id>#{contact.tags[1].id}</id>}
188
+ xml.should match %r{<name>awesome</name>}
189
+ xml.should match %r{<name>ruby</name>}
190
+ end
191
+
192
+ it "should include dynamic attributes" do
193
+ contact = Contact.new(:name => 'John', :age => 27, :foo => 'bar')
194
+ contact['smell'] = 'stinky'
195
+ contact.to_xml.should match %r{<smell>stinky</smell>}
196
+ end
197
+ end
198
+ end
@@ -1,27 +1,27 @@
1
- require 'test_helper'
1
+ require 'spec_helper'
2
2
 
3
- class TimeZonesTest < Test::Unit::TestCase
3
+ describe "TimeZones" do
4
4
  context "An instance of an embedded document" do
5
- setup do
5
+ before do
6
6
  @document = EDoc do
7
7
  key :name, String
8
8
  key :created_at, Time
9
9
  end
10
10
  end
11
11
 
12
- should "preserve milliseconds" do
12
+ it "should preserve milliseconds" do
13
13
  doc = @document.new(:created_at => '2011-02-12 16:01:02.543Z')
14
- doc.created_at.should be_close(Time.parse('2011-02-12 16:01:02.543Z'), 0.0000001)
14
+ doc.created_at.should be_within(0.0000001).of(Time.parse('2011-02-12 16:01:02.543Z'))
15
15
  end
16
16
 
17
- should "work without Time.zone" do
17
+ it "should work without Time.zone" do
18
18
  Time.zone = nil
19
19
 
20
20
  doc = @document.new(:created_at => "2009-08-15 14:00:00")
21
21
  doc.created_at.should == Time.local(2009, 8, 15, 14, 0, 0).utc
22
22
  end
23
23
 
24
- should "work with Time.zone set to the (default) UTC" do
24
+ it "should work with Time.zone set to the (default) UTC" do
25
25
  Time.zone = 'UTC'
26
26
 
27
27
  doc = @document.new(:created_at => "2009-08-15 14:00:00")
@@ -31,7 +31,7 @@ class TimeZonesTest < Test::Unit::TestCase
31
31
  Time.zone = nil
32
32
  end
33
33
 
34
- should "work with timezones that are not UTC" do
34
+ it "should work with timezones that are not UTC" do
35
35
  Time.zone = 'Hawaii'
36
36
 
37
37
  doc = @document.new(:created_at => "2009-08-15 14:00:00")