active_model_serializers 0.10.0 → 0.10.7

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 (171) hide show
  1. checksums.yaml +5 -5
  2. data/.rubocop.yml +6 -5
  3. data/.travis.yml +30 -21
  4. data/CHANGELOG.md +172 -2
  5. data/CODE_OF_CONDUCT.md +74 -0
  6. data/Gemfile +23 -4
  7. data/README.md +166 -28
  8. data/Rakefile +3 -32
  9. data/active_model_serializers.gemspec +22 -25
  10. data/appveyor.yml +10 -6
  11. data/bin/rubocop +38 -0
  12. data/docs/README.md +2 -1
  13. data/docs/general/adapters.md +35 -11
  14. data/docs/general/caching.md +7 -1
  15. data/docs/general/configuration_options.md +86 -1
  16. data/docs/general/deserialization.md +1 -1
  17. data/docs/general/fields.md +31 -0
  18. data/docs/general/getting_started.md +1 -1
  19. data/docs/general/logging.md +7 -0
  20. data/docs/general/rendering.md +63 -25
  21. data/docs/general/serializers.md +125 -14
  22. data/docs/howto/add_pagination_links.md +16 -17
  23. data/docs/howto/add_relationship_links.md +140 -0
  24. data/docs/howto/add_root_key.md +11 -0
  25. data/docs/howto/grape_integration.md +42 -0
  26. data/docs/howto/outside_controller_use.md +12 -4
  27. data/docs/howto/passing_arbitrary_options.md +2 -2
  28. data/docs/howto/serialize_poro.md +46 -5
  29. data/docs/howto/test.md +2 -0
  30. data/docs/howto/upgrade_from_0_8_to_0_10.md +265 -0
  31. data/docs/integrations/ember-and-json-api.md +67 -32
  32. data/docs/jsonapi/schema.md +1 -1
  33. data/lib/action_controller/serialization.rb +13 -3
  34. data/lib/active_model/serializer/adapter/base.rb +2 -0
  35. data/lib/active_model/serializer/array_serializer.rb +8 -5
  36. data/lib/active_model/serializer/association.rb +62 -10
  37. data/lib/active_model/serializer/belongs_to_reflection.rb +4 -3
  38. data/lib/active_model/serializer/collection_serializer.rb +39 -13
  39. data/lib/active_model/serializer/{caching.rb → concerns/caching.rb} +82 -115
  40. data/lib/active_model/serializer/error_serializer.rb +11 -7
  41. data/lib/active_model/serializer/errors_serializer.rb +25 -20
  42. data/lib/active_model/serializer/has_many_reflection.rb +3 -3
  43. data/lib/active_model/serializer/has_one_reflection.rb +1 -4
  44. data/lib/active_model/serializer/lazy_association.rb +95 -0
  45. data/lib/active_model/serializer/lint.rb +134 -130
  46. data/lib/active_model/serializer/reflection.rb +127 -67
  47. data/lib/active_model/serializer/version.rb +1 -1
  48. data/lib/active_model/serializer.rb +297 -79
  49. data/lib/active_model_serializers/adapter/attributes.rb +3 -66
  50. data/lib/active_model_serializers/adapter/base.rb +39 -39
  51. data/lib/active_model_serializers/adapter/json_api/deserialization.rb +2 -2
  52. data/lib/active_model_serializers/adapter/json_api/link.rb +1 -1
  53. data/lib/active_model_serializers/adapter/json_api/pagination_links.rb +47 -21
  54. data/lib/active_model_serializers/adapter/json_api/relationship.rb +75 -23
  55. data/lib/active_model_serializers/adapter/json_api/resource_identifier.rb +39 -10
  56. data/lib/active_model_serializers/adapter/json_api.rb +71 -57
  57. data/lib/active_model_serializers/adapter.rb +6 -0
  58. data/lib/active_model_serializers/deprecate.rb +1 -2
  59. data/lib/active_model_serializers/deserialization.rb +2 -0
  60. data/lib/active_model_serializers/lookup_chain.rb +80 -0
  61. data/lib/active_model_serializers/model.rb +109 -28
  62. data/lib/active_model_serializers/railtie.rb +3 -1
  63. data/lib/active_model_serializers/register_jsonapi_renderer.rb +44 -31
  64. data/lib/active_model_serializers/serializable_resource.rb +6 -5
  65. data/lib/active_model_serializers/serialization_context.rb +10 -3
  66. data/lib/active_model_serializers/test/schema.rb +2 -2
  67. data/lib/active_model_serializers.rb +16 -1
  68. data/lib/generators/rails/resource_override.rb +1 -1
  69. data/lib/generators/rails/serializer_generator.rb +4 -4
  70. data/lib/grape/active_model_serializers.rb +7 -5
  71. data/lib/grape/formatters/active_model_serializers.rb +19 -2
  72. data/lib/grape/helpers/active_model_serializers.rb +1 -0
  73. data/lib/tasks/rubocop.rake +53 -0
  74. data/test/action_controller/adapter_selector_test.rb +14 -5
  75. data/test/action_controller/explicit_serializer_test.rb +5 -4
  76. data/test/action_controller/json/include_test.rb +106 -27
  77. data/test/action_controller/json_api/deserialization_test.rb +1 -1
  78. data/test/action_controller/json_api/errors_test.rb +8 -9
  79. data/test/action_controller/json_api/fields_test.rb +66 -0
  80. data/test/action_controller/json_api/linked_test.rb +29 -24
  81. data/test/action_controller/json_api/pagination_test.rb +31 -23
  82. data/test/action_controller/json_api/transform_test.rb +11 -3
  83. data/test/action_controller/lookup_proc_test.rb +49 -0
  84. data/test/action_controller/namespace_lookup_test.rb +232 -0
  85. data/test/action_controller/serialization_scope_name_test.rb +12 -6
  86. data/test/action_controller/serialization_test.rb +12 -9
  87. data/test/active_model_serializers/json_pointer_test.rb +15 -13
  88. data/test/active_model_serializers/model_test.rb +137 -4
  89. data/test/active_model_serializers/railtie_test_isolated.rb +12 -7
  90. data/test/active_model_serializers/register_jsonapi_renderer_test_isolated.rb +161 -0
  91. data/test/active_model_serializers/serialization_context_test_isolated.rb +23 -10
  92. data/test/active_model_serializers/test/schema_test.rb +3 -2
  93. data/test/adapter/attributes_test.rb +40 -0
  94. data/test/adapter/json/collection_test.rb +14 -0
  95. data/test/adapter/json/has_many_test.rb +10 -2
  96. data/test/adapter/json/transform_test.rb +15 -15
  97. data/test/adapter/json_api/collection_test.rb +4 -3
  98. data/test/adapter/json_api/errors_test.rb +17 -19
  99. data/test/adapter/json_api/fields_test.rb +12 -3
  100. data/test/adapter/json_api/has_many_test.rb +49 -20
  101. data/test/adapter/json_api/include_data_if_sideloaded_test.rb +213 -0
  102. data/test/adapter/json_api/json_api_test.rb +5 -7
  103. data/test/adapter/json_api/linked_test.rb +33 -12
  104. data/test/adapter/json_api/links_test.rb +4 -2
  105. data/test/adapter/json_api/pagination_links_test.rb +53 -13
  106. data/test/adapter/json_api/parse_test.rb +1 -1
  107. data/test/adapter/json_api/relationship_test.rb +309 -73
  108. data/test/adapter/json_api/resource_meta_test.rb +3 -3
  109. data/test/adapter/json_api/transform_test.rb +263 -253
  110. data/test/adapter/json_api/type_test.rb +168 -36
  111. data/test/adapter/json_test.rb +8 -7
  112. data/test/adapter/null_test.rb +1 -2
  113. data/test/adapter/polymorphic_test.rb +52 -5
  114. data/test/adapter_test.rb +1 -1
  115. data/test/benchmark/app.rb +1 -1
  116. data/test/benchmark/benchmarking_support.rb +1 -1
  117. data/test/benchmark/bm_active_record.rb +81 -0
  118. data/test/benchmark/bm_adapter.rb +38 -0
  119. data/test/benchmark/bm_caching.rb +16 -16
  120. data/test/benchmark/bm_lookup_chain.rb +83 -0
  121. data/test/benchmark/bm_transform.rb +21 -10
  122. data/test/benchmark/controllers.rb +16 -17
  123. data/test/benchmark/fixtures.rb +72 -72
  124. data/test/cache_test.rb +235 -69
  125. data/test/collection_serializer_test.rb +31 -14
  126. data/test/fixtures/active_record.rb +45 -10
  127. data/test/fixtures/poro.rb +124 -181
  128. data/test/generators/serializer_generator_test.rb +23 -5
  129. data/test/grape_test.rb +170 -56
  130. data/test/lint_test.rb +1 -1
  131. data/test/logger_test.rb +13 -11
  132. data/test/serializable_resource_test.rb +18 -22
  133. data/test/serializers/association_macros_test.rb +3 -2
  134. data/test/serializers/associations_test.rb +222 -49
  135. data/test/serializers/attribute_test.rb +5 -3
  136. data/test/serializers/attributes_test.rb +1 -1
  137. data/test/serializers/caching_configuration_test_isolated.rb +6 -6
  138. data/test/serializers/fieldset_test.rb +1 -1
  139. data/test/serializers/meta_test.rb +12 -6
  140. data/test/serializers/options_test.rb +17 -6
  141. data/test/serializers/read_attribute_for_serialization_test.rb +3 -3
  142. data/test/serializers/reflection_test.rb +427 -0
  143. data/test/serializers/root_test.rb +1 -1
  144. data/test/serializers/serialization_test.rb +2 -2
  145. data/test/serializers/serializer_for_test.rb +12 -10
  146. data/test/serializers/serializer_for_with_namespace_test.rb +88 -0
  147. data/test/support/isolated_unit.rb +9 -4
  148. data/test/support/rails5_shims.rb +8 -2
  149. data/test/support/rails_app.rb +2 -9
  150. data/test/support/serialization_testing.rb +31 -5
  151. data/test/test_helper.rb +13 -0
  152. metadata +130 -71
  153. data/.rubocop_todo.yml +0 -167
  154. data/docs/ARCHITECTURE.md +0 -126
  155. data/lib/active_model/serializer/associations.rb +0 -100
  156. data/lib/active_model/serializer/attributes.rb +0 -82
  157. data/lib/active_model/serializer/collection_reflection.rb +0 -7
  158. data/lib/active_model/serializer/configuration.rb +0 -35
  159. data/lib/active_model/serializer/include_tree.rb +0 -111
  160. data/lib/active_model/serializer/links.rb +0 -35
  161. data/lib/active_model/serializer/meta.rb +0 -29
  162. data/lib/active_model/serializer/singular_reflection.rb +0 -7
  163. data/lib/active_model/serializer/type.rb +0 -25
  164. data/lib/active_model_serializers/key_transform.rb +0 -70
  165. data/test/active_model_serializers/key_transform_test.rb +0 -263
  166. data/test/adapter/json_api/has_many_embed_ids_test.rb +0 -43
  167. data/test/adapter/json_api/relationships_test.rb +0 -199
  168. data/test/adapter/json_api/resource_identifier_test.rb +0 -85
  169. data/test/include_tree/from_include_args_test.rb +0 -26
  170. data/test/include_tree/from_string_test.rb +0 -94
  171. data/test/include_tree/include_args_to_hash_test.rb +0 -64
@@ -0,0 +1,232 @@
1
+ require 'test_helper'
2
+
3
+ module ActionController
4
+ module Serialization
5
+ class NamespaceLookupTest < ActionController::TestCase
6
+ class Book < ::Model
7
+ attributes :id, :title, :body
8
+ associations :writer, :chapters
9
+ end
10
+ class Chapter < ::Model
11
+ attributes :title
12
+ end
13
+ class Writer < ::Model
14
+ attributes :name
15
+ end
16
+
17
+ module Api
18
+ module V2
19
+ class BookSerializer < ActiveModel::Serializer
20
+ attributes :title
21
+ end
22
+ end
23
+
24
+ module VHeader
25
+ class BookSerializer < ActiveModel::Serializer
26
+ attributes :title, :body
27
+
28
+ def body
29
+ 'header'
30
+ end
31
+ end
32
+ end
33
+
34
+ module V3
35
+ class BookSerializer < ActiveModel::Serializer
36
+ attributes :title, :body
37
+
38
+ belongs_to :writer
39
+ has_many :chapters
40
+ end
41
+
42
+ class ChapterSerializer < ActiveModel::Serializer
43
+ attribute :title do
44
+ "Chapter - #{object.title}"
45
+ end
46
+ end
47
+
48
+ class WriterSerializer < ActiveModel::Serializer
49
+ attributes :name
50
+ end
51
+
52
+ class LookupTestController < ActionController::Base
53
+ before_action only: [:namespace_set_in_before_filter] do
54
+ self.namespace_for_serializer = Api::V2
55
+ end
56
+
57
+ def implicit_namespaced_serializer
58
+ writer = Writer.new(name: 'Bob')
59
+ book = Book.new(title: 'New Post', body: 'Body', writer: writer, chapters: [])
60
+
61
+ render json: book
62
+ end
63
+
64
+ def implicit_namespaced_collection_serializer
65
+ chapter1 = Chapter.new(title: 'Oh')
66
+ chapter2 = Chapter.new(title: 'Oh my')
67
+
68
+ render json: [chapter1, chapter2]
69
+ end
70
+
71
+ def implicit_has_many_namespaced_serializer
72
+ chapter1 = Chapter.new(title: 'Odd World')
73
+ chapter2 = Chapter.new(title: 'New World')
74
+ book = Book.new(title: 'New Post', body: 'Body', chapters: [chapter1, chapter2])
75
+
76
+ render json: book
77
+ end
78
+
79
+ def explicit_namespace_as_module
80
+ book = Book.new(title: 'New Post', body: 'Body')
81
+
82
+ render json: book, namespace: Api::V2
83
+ end
84
+
85
+ def explicit_namespace_as_string
86
+ book = Book.new(title: 'New Post', body: 'Body')
87
+
88
+ # because this is a string, ruby can't auto-lookup the constant, so otherwise
89
+ # the lookup thinks we mean ::Api::V2
90
+ render json: book, namespace: 'ActionController::Serialization::NamespaceLookupTest::Api::V2'
91
+ end
92
+
93
+ def explicit_namespace_as_symbol
94
+ book = Book.new(title: 'New Post', body: 'Body')
95
+
96
+ # because this is a string, ruby can't auto-lookup the constant, so otherwise
97
+ # the lookup thinks we mean ::Api::V2
98
+ render json: book, namespace: :'ActionController::Serialization::NamespaceLookupTest::Api::V2'
99
+ end
100
+
101
+ def invalid_namespace
102
+ book = Book.new(id: 'invalid_namespace_book_id', title: 'New Post', body: 'Body')
103
+
104
+ render json: book, namespace: :api_v2
105
+ end
106
+
107
+ def namespace_set_in_before_filter
108
+ book = Book.new(title: 'New Post', body: 'Body')
109
+ render json: book
110
+ end
111
+
112
+ def namespace_set_by_request_headers
113
+ book = Book.new(title: 'New Post', body: 'Body')
114
+ version_from_header = request.headers['X-API_VERSION']
115
+ namespace = "ActionController::Serialization::NamespaceLookupTest::#{version_from_header}"
116
+
117
+ render json: book, namespace: namespace
118
+ end
119
+ end
120
+ end
121
+ end
122
+
123
+ tests Api::V3::LookupTestController
124
+
125
+ setup do
126
+ @test_namespace = self.class.parent
127
+ end
128
+
129
+ test 'uses request headers to determine the namespace' do
130
+ request.env['X-API_VERSION'] = 'Api::VHeader'
131
+ get :namespace_set_by_request_headers
132
+
133
+ assert_serializer Api::VHeader::BookSerializer
134
+ end
135
+
136
+ test 'implicitly uses namespaced serializer' do
137
+ get :implicit_namespaced_serializer
138
+
139
+ assert_serializer Api::V3::BookSerializer
140
+
141
+ expected = { 'title' => 'New Post', 'body' => 'Body', 'writer' => { 'name' => 'Bob' }, 'chapters' => [] }
142
+ actual = JSON.parse(@response.body)
143
+
144
+ assert_equal expected, actual
145
+ end
146
+
147
+ test 'implicitly uses namespaced serializer for collection' do
148
+ get :implicit_namespaced_collection_serializer
149
+
150
+ assert_serializer 'ActiveModel::Serializer::CollectionSerializer'
151
+
152
+ expected = [{ 'title' => 'Chapter - Oh' }, { 'title' => 'Chapter - Oh my' }]
153
+ actual = JSON.parse(@response.body)
154
+
155
+ assert_equal expected, actual
156
+ end
157
+
158
+ test 'implicitly uses namespaced serializer for has_many' do
159
+ get :implicit_has_many_namespaced_serializer
160
+
161
+ assert_serializer Api::V3::BookSerializer
162
+
163
+ expected = {
164
+ 'title' => 'New Post',
165
+ 'body' => 'Body', 'writer' => nil,
166
+ 'chapters' => [
167
+ { 'title' => 'Chapter - Odd World' },
168
+ { 'title' => 'Chapter - New World' }
169
+ ]
170
+ }
171
+ actual = JSON.parse(@response.body)
172
+
173
+ assert_equal expected, actual
174
+ end
175
+
176
+ test 'explicit namespace as module' do
177
+ get :explicit_namespace_as_module
178
+
179
+ assert_serializer Api::V2::BookSerializer
180
+
181
+ expected = { 'title' => 'New Post' }
182
+ actual = JSON.parse(@response.body)
183
+
184
+ assert_equal expected, actual
185
+ end
186
+
187
+ test 'explicit namespace as string' do
188
+ get :explicit_namespace_as_string
189
+
190
+ assert_serializer Api::V2::BookSerializer
191
+
192
+ expected = { 'title' => 'New Post' }
193
+ actual = JSON.parse(@response.body)
194
+
195
+ assert_equal expected, actual
196
+ end
197
+
198
+ test 'explicit namespace as symbol' do
199
+ get :explicit_namespace_as_symbol
200
+
201
+ assert_serializer Api::V2::BookSerializer
202
+
203
+ expected = { 'title' => 'New Post' }
204
+ actual = JSON.parse(@response.body)
205
+
206
+ assert_equal expected, actual
207
+ end
208
+
209
+ test 'invalid namespace' do
210
+ get :invalid_namespace
211
+
212
+ assert_serializer ActiveModel::Serializer::Null
213
+
214
+ expected = { 'id' => 'invalid_namespace_book_id', 'title' => 'New Post', 'body' => 'Body' }
215
+ actual = JSON.parse(@response.body)
216
+
217
+ assert_equal expected, actual
218
+ end
219
+
220
+ test 'namespace set in before filter' do
221
+ get :namespace_set_in_before_filter
222
+
223
+ assert_serializer Api::V2::BookSerializer
224
+
225
+ expected = { 'title' => 'New Post' }
226
+ actual = JSON.parse(@response.body)
227
+
228
+ assert_equal expected, actual
229
+ end
230
+ end
231
+ end
232
+ end
@@ -2,16 +2,16 @@ require 'test_helper'
2
2
 
3
3
  module SerializationScopeTesting
4
4
  class User < ActiveModelSerializers::Model
5
- attr_accessor :id, :name, :admin
5
+ attributes :id, :name, :admin
6
6
  def admin?
7
7
  admin
8
8
  end
9
9
  end
10
10
  class Comment < ActiveModelSerializers::Model
11
- attr_accessor :id, :body
11
+ attributes :id, :body
12
12
  end
13
13
  class Post < ActiveModelSerializers::Model
14
- attr_accessor :id, :title, :body, :comments
14
+ attributes :id, :title, :body, :comments
15
15
  end
16
16
  class PostSerializer < ActiveModel::Serializer
17
17
  attributes :id, :title, :body, :comments
@@ -33,7 +33,8 @@ module SerializationScopeTesting
33
33
  end
34
34
  end
35
35
  class PostTestController < ActionController::Base
36
- attr_accessor :current_user
36
+ attr_writer :current_user
37
+
37
38
  def render_post_by_non_admin
38
39
  self.current_user = User.new(id: 3, name: 'Pete', admin: false)
39
40
  render json: new_post, serializer: serializer, adapter: :json
@@ -44,6 +45,10 @@ module SerializationScopeTesting
44
45
  render json: new_post, serializer: serializer, adapter: :json
45
46
  end
46
47
 
48
+ def current_user
49
+ defined?(@current_user) ? @current_user : :current_user_not_set
50
+ end
51
+
47
52
  private
48
53
 
49
54
  def new_post
@@ -75,7 +80,8 @@ module SerializationScopeTesting
75
80
  end
76
81
 
77
82
  def test_default_serialization_scope_object
78
- assert_equal @controller.current_user, @controller.serialization_scope
83
+ assert_equal :current_user_not_set, @controller.current_user
84
+ assert_equal :current_user_not_set, @controller.serialization_scope
79
85
  end
80
86
 
81
87
  def test_default_scope_non_admin
@@ -125,7 +131,7 @@ module SerializationScopeTesting
125
131
  end
126
132
 
127
133
  def test_defined_serialization_scope_object
128
- assert_equal @controller.view_context.class, @controller.serialization_scope.class
134
+ assert_equal @controller.view_context.controller, @controller.serialization_scope.controller
129
135
  end
130
136
 
131
137
  def test_serialization_scope_non_admin
@@ -74,7 +74,7 @@ module ActionController
74
74
  end
75
75
 
76
76
  def update_and_render_object_with_cache_enabled
77
- @post.updated_at = Time.now
77
+ @post.updated_at = Time.zone.now
78
78
 
79
79
  generate_cached_serializer(@post)
80
80
  render json: @post
@@ -135,7 +135,7 @@ module ActionController
135
135
  like = Like.new(id: 1, likeable: comment, time: 3.days.ago)
136
136
 
137
137
  generate_cached_serializer(like)
138
- like.likable = comment2
138
+ like.likeable = comment2
139
139
  like.time = Time.zone.now.to_s
140
140
 
141
141
  render json: like
@@ -163,7 +163,7 @@ module ActionController
163
163
  end
164
164
  expected = {
165
165
  data: {
166
- id: assigns(:profile).id.to_s,
166
+ id: @controller.instance_variable_get(:@profile).id.to_s,
167
167
  type: 'profiles',
168
168
  attributes: {
169
169
  name: 'Name 1',
@@ -246,7 +246,7 @@ module ActionController
246
246
  expected = {
247
247
  data: [
248
248
  {
249
- id: assigns(:profiles).first.id.to_s,
249
+ id: @controller.instance_variable_get(:@profiles).first.id.to_s,
250
250
  type: 'profiles',
251
251
  attributes: {
252
252
  name: 'Name 1',
@@ -269,7 +269,7 @@ module ActionController
269
269
  expected = {
270
270
  data: [
271
271
  {
272
- id: assigns(:profiles).first.id.to_s,
272
+ id: @controller.instance_variable_get(:@profiles).first.id.to_s,
273
273
  type: 'profiles',
274
274
  attributes: {
275
275
  name: 'Name 1',
@@ -294,7 +294,8 @@ module ActionController
294
294
  comments: [
295
295
  {
296
296
  id: 1,
297
- body: 'ZOMG A COMMENT' }
297
+ body: 'ZOMG A COMMENT'
298
+ }
298
299
  ],
299
300
  blog: {
300
301
  id: 999,
@@ -333,7 +334,8 @@ module ActionController
333
334
  comments: [
334
335
  {
335
336
  id: 1,
336
- body: 'ZOMG A COMMENT' }
337
+ body: 'ZOMG A COMMENT'
338
+ }
337
339
  ],
338
340
  blog: {
339
341
  id: 999,
@@ -407,7 +409,8 @@ module ActionController
407
409
  comments: [
408
410
  {
409
411
  id: 1,
410
- body: 'ZOMG A COMMENT' }
412
+ body: 'ZOMG A COMMENT'
413
+ }
411
414
  ],
412
415
  blog: {
413
416
  id: 999,
@@ -453,7 +456,7 @@ module ActionController
453
456
  end
454
457
  end
455
458
 
456
- def test_render_event_is_emmited
459
+ def test_render_event_is_emitted
457
460
  subscriber = ::ActiveSupport::Notifications.subscribe('render.active_model_serializers') do |name|
458
461
  @name = name
459
462
  end
@@ -1,20 +1,22 @@
1
1
  require 'test_helper'
2
2
 
3
- class ActiveModelSerializers::JsonPointerTest < ActiveSupport::TestCase
4
- def test_attribute_pointer
5
- attribute_name = 'title'
6
- pointer = ActiveModelSerializers::JsonPointer.new(:attribute, attribute_name)
7
- assert_equal '/data/attributes/title', pointer
8
- end
3
+ module ActiveModelSerializers
4
+ class JsonPointerTest < ActiveSupport::TestCase
5
+ def test_attribute_pointer
6
+ attribute_name = 'title'
7
+ pointer = ActiveModelSerializers::JsonPointer.new(:attribute, attribute_name)
8
+ assert_equal '/data/attributes/title', pointer
9
+ end
9
10
 
10
- def test_primary_data_pointer
11
- pointer = ActiveModelSerializers::JsonPointer.new(:primary_data)
12
- assert_equal '/data', pointer
13
- end
11
+ def test_primary_data_pointer
12
+ pointer = ActiveModelSerializers::JsonPointer.new(:primary_data)
13
+ assert_equal '/data', pointer
14
+ end
14
15
 
15
- def test_unkown_data_pointer
16
- assert_raises(TypeError) do
17
- ActiveModelSerializers::JsonPointer.new(:unknown)
16
+ def test_unknown_data_pointer
17
+ assert_raises(TypeError) do
18
+ ActiveModelSerializers::JsonPointer.new(:unknown)
19
+ end
18
20
  end
19
21
  end
20
22
  end
@@ -1,9 +1,142 @@
1
1
  require 'test_helper'
2
2
 
3
- class ActiveModelSerializers::ModelTest < ActiveSupport::TestCase
4
- include ActiveModel::Serializer::Lint::Tests
3
+ module ActiveModelSerializers
4
+ class ModelTest < ActiveSupport::TestCase
5
+ include ActiveModel::Serializer::Lint::Tests
5
6
 
6
- def setup
7
- @resource = ActiveModelSerializers::Model.new
7
+ setup do
8
+ @resource = ActiveModelSerializers::Model.new
9
+ end
10
+
11
+ def test_initialization_with_string_keys
12
+ klass = Class.new(ActiveModelSerializers::Model) do
13
+ attributes :key
14
+ end
15
+ value = 'value'
16
+
17
+ model_instance = klass.new('key' => value)
18
+
19
+ assert_equal model_instance.read_attribute_for_serialization(:key), value
20
+ end
21
+
22
+ def test_attributes_can_be_read_for_serialization
23
+ klass = Class.new(ActiveModelSerializers::Model) do
24
+ attributes :one, :two, :three
25
+ end
26
+ original_attributes = { one: 1, two: 2, three: 3 }
27
+ original_instance = klass.new(original_attributes)
28
+
29
+ # Initial value
30
+ instance = original_instance
31
+ expected_attributes = { one: 1, two: 2, three: 3 }.with_indifferent_access
32
+ assert_equal expected_attributes, instance.attributes
33
+ assert_equal 1, instance.one
34
+ assert_equal 1, instance.read_attribute_for_serialization(:one)
35
+
36
+ # FIXME: Change via accessor has no effect on attributes.
37
+ instance = original_instance.dup
38
+ instance.one = :not_one
39
+ assert_equal expected_attributes, instance.attributes
40
+ assert_equal :not_one, instance.one
41
+ assert_equal :not_one, instance.read_attribute_for_serialization(:one)
42
+
43
+ # FIXME: Change via mutating attributes
44
+ instance = original_instance.dup
45
+ instance.attributes[:one] = :not_one
46
+ expected_attributes = { one: :not_one, two: 2, three: 3 }.with_indifferent_access
47
+ assert_equal expected_attributes, instance.attributes
48
+ assert_equal 1, instance.one
49
+ assert_equal 1, instance.read_attribute_for_serialization(:one)
50
+ end
51
+
52
+ def test_attributes_can_be_read_for_serialization_with_attributes_accessors_fix
53
+ klass = Class.new(ActiveModelSerializers::Model) do
54
+ derive_attributes_from_names_and_fix_accessors
55
+ attributes :one, :two, :three
56
+ end
57
+ original_attributes = { one: 1, two: 2, three: 3 }
58
+ original_instance = klass.new(original_attributes)
59
+
60
+ # Initial value
61
+ instance = original_instance
62
+ expected_attributes = { one: 1, two: 2, three: 3 }.with_indifferent_access
63
+ assert_equal expected_attributes, instance.attributes
64
+ assert_equal 1, instance.one
65
+ assert_equal 1, instance.read_attribute_for_serialization(:one)
66
+
67
+ expected_attributes = { one: :not_one, two: 2, three: 3 }.with_indifferent_access
68
+ # Change via accessor
69
+ instance = original_instance.dup
70
+ instance.one = :not_one
71
+ assert_equal expected_attributes, instance.attributes
72
+ assert_equal :not_one, instance.one
73
+ assert_equal :not_one, instance.read_attribute_for_serialization(:one)
74
+
75
+ # Attributes frozen
76
+ assert instance.attributes.frozen?
77
+ end
78
+
79
+ def test_id_attribute_can_be_read_for_serialization
80
+ klass = Class.new(ActiveModelSerializers::Model) do
81
+ attributes :id, :one, :two, :three
82
+ end
83
+ self.class.const_set(:SomeTestModel, klass)
84
+ original_attributes = { id: :ego, one: 1, two: 2, three: 3 }
85
+ original_instance = klass.new(original_attributes)
86
+
87
+ # Initial value
88
+ instance = original_instance.dup
89
+ expected_attributes = { id: :ego, one: 1, two: 2, three: 3 }.with_indifferent_access
90
+ assert_equal expected_attributes, instance.attributes
91
+ assert_equal :ego, instance.id
92
+ assert_equal :ego, instance.read_attribute_for_serialization(:id)
93
+
94
+ # FIXME: Change via accessor has no effect on attributes.
95
+ instance = original_instance.dup
96
+ instance.id = :superego
97
+ assert_equal expected_attributes, instance.attributes
98
+ assert_equal :superego, instance.id
99
+ assert_equal :superego, instance.read_attribute_for_serialization(:id)
100
+
101
+ # FIXME: Change via mutating attributes
102
+ instance = original_instance.dup
103
+ instance.attributes[:id] = :superego
104
+ expected_attributes = { id: :superego, one: 1, two: 2, three: 3 }.with_indifferent_access
105
+ assert_equal expected_attributes, instance.attributes
106
+ assert_equal :ego, instance.id
107
+ assert_equal :ego, instance.read_attribute_for_serialization(:id)
108
+ ensure
109
+ self.class.send(:remove_const, :SomeTestModel)
110
+ end
111
+
112
+ def test_id_attribute_can_be_read_for_serialization_with_attributes_accessors_fix
113
+ klass = Class.new(ActiveModelSerializers::Model) do
114
+ derive_attributes_from_names_and_fix_accessors
115
+ attributes :id, :one, :two, :three
116
+ end
117
+ self.class.const_set(:SomeTestModel, klass)
118
+ original_attributes = { id: :ego, one: 1, two: 2, three: 3 }
119
+ original_instance = klass.new(original_attributes)
120
+
121
+ # Initial value
122
+ instance = original_instance.dup
123
+ expected_attributes = { id: :ego, one: 1, two: 2, three: 3 }.with_indifferent_access
124
+ assert_equal expected_attributes, instance.attributes
125
+ assert_equal :ego, instance.id
126
+ assert_equal :ego, instance.read_attribute_for_serialization(:id)
127
+
128
+ expected_attributes = { id: :superego, one: 1, two: 2, three: 3 }.with_indifferent_access
129
+ # Change via accessor
130
+ instance = original_instance.dup
131
+ instance.id = :superego
132
+ assert_equal expected_attributes, instance.attributes
133
+ assert_equal :superego, instance.id
134
+ assert_equal :superego, instance.read_attribute_for_serialization(:id)
135
+
136
+ # Attributes frozen
137
+ assert instance.attributes.frozen?
138
+ ensure
139
+ self.class.send(:remove_const, :SomeTestModel)
140
+ end
8
141
  end
9
142
  end
@@ -4,11 +4,13 @@ require 'support/isolated_unit'
4
4
  class RailtieTest < ActiveSupport::TestCase
5
5
  include ActiveSupport::Testing::Isolation
6
6
 
7
- class WithRails < RailtieTest
7
+ class WithRailsRequiredFirst < RailtieTest
8
8
  setup do
9
9
  require 'rails'
10
10
  require 'active_model_serializers'
11
- make_basic_app
11
+ make_basic_app do |app|
12
+ app.config.action_controller.perform_caching = true
13
+ end
12
14
  end
13
15
 
14
16
  test 'mixes ActionController::Serialization into ActionController::Base' do
@@ -32,14 +34,17 @@ class RailtieTest < ActiveSupport::TestCase
32
34
 
33
35
  test 'it is configured for caching' do
34
36
  assert_equal ActionController::Base.cache_store, ActiveModelSerializers.config.cache_store
35
- assert_equal Rails.configuration.action_controller.perform_caching, ActiveModelSerializers.config.perform_caching
37
+ assert_equal true, Rails.configuration.action_controller.perform_caching
38
+ assert_equal true, ActiveModelSerializers.config.perform_caching
36
39
  end
37
40
  end
38
41
 
39
- class WithoutRails < RailtieTest
42
+ class WithoutRailsRequiredFirst < RailtieTest
40
43
  setup do
41
44
  require 'active_model_serializers'
42
- make_basic_app
45
+ make_basic_app do |app|
46
+ app.config.action_controller.perform_caching = true
47
+ end
43
48
  end
44
49
 
45
50
  test 'does not mix ActionController::Serialization into ActionController::Base' do
@@ -56,8 +61,8 @@ class RailtieTest < ActiveSupport::TestCase
56
61
  test 'it is not configured for caching' do
57
62
  refute_nil ActionController::Base.cache_store
58
63
  assert_nil ActiveModelSerializers.config.cache_store
59
- refute Rails.configuration.action_controller.perform_caching
60
- refute ActiveModelSerializers.config.perform_caching
64
+ assert_equal true, Rails.configuration.action_controller.perform_caching
65
+ assert_nil ActiveModelSerializers.config.perform_caching
61
66
  end
62
67
  end
63
68
  end