agi_active_model_serializers 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 (220) hide show
  1. checksums.yaml +7 -0
  2. data/.github/ISSUE_TEMPLATE.md +29 -0
  3. data/.github/PULL_REQUEST_TEMPLATE.md +15 -0
  4. data/.gitignore +35 -0
  5. data/.rubocop.yml +102 -0
  6. data/.simplecov +110 -0
  7. data/.travis.yml +51 -0
  8. data/CHANGELOG.md +612 -0
  9. data/CODE_OF_CONDUCT.md +74 -0
  10. data/CONTRIBUTING.md +105 -0
  11. data/Gemfile +56 -0
  12. data/MIT-LICENSE +22 -0
  13. data/README.md +307 -0
  14. data/Rakefile +103 -0
  15. data/active_model_serializers.gemspec +63 -0
  16. data/appveyor.yml +24 -0
  17. data/bin/bench +171 -0
  18. data/bin/bench_regression +316 -0
  19. data/bin/serve_benchmark +39 -0
  20. data/docs/README.md +41 -0
  21. data/docs/STYLE.md +58 -0
  22. data/docs/general/adapters.md +247 -0
  23. data/docs/general/caching.md +58 -0
  24. data/docs/general/configuration_options.md +169 -0
  25. data/docs/general/deserialization.md +100 -0
  26. data/docs/general/fields.md +31 -0
  27. data/docs/general/getting_started.md +133 -0
  28. data/docs/general/instrumentation.md +40 -0
  29. data/docs/general/key_transforms.md +40 -0
  30. data/docs/general/logging.md +14 -0
  31. data/docs/general/rendering.md +279 -0
  32. data/docs/general/serializers.md +461 -0
  33. data/docs/how-open-source-maintained.jpg +0 -0
  34. data/docs/howto/add_pagination_links.md +138 -0
  35. data/docs/howto/add_relationship_links.md +137 -0
  36. data/docs/howto/add_root_key.md +55 -0
  37. data/docs/howto/grape_integration.md +42 -0
  38. data/docs/howto/outside_controller_use.md +65 -0
  39. data/docs/howto/passing_arbitrary_options.md +27 -0
  40. data/docs/howto/serialize_poro.md +32 -0
  41. data/docs/howto/test.md +154 -0
  42. data/docs/howto/upgrade_from_0_8_to_0_10.md +265 -0
  43. data/docs/integrations/ember-and-json-api.md +144 -0
  44. data/docs/integrations/grape.md +19 -0
  45. data/docs/jsonapi/errors.md +56 -0
  46. data/docs/jsonapi/schema.md +151 -0
  47. data/docs/jsonapi/schema/schema.json +366 -0
  48. data/docs/rfcs/0000-namespace.md +106 -0
  49. data/docs/rfcs/template.md +15 -0
  50. data/lib/action_controller/serialization.rb +66 -0
  51. data/lib/active_model/serializable_resource.rb +11 -0
  52. data/lib/active_model/serializer.rb +231 -0
  53. data/lib/active_model/serializer/adapter.rb +24 -0
  54. data/lib/active_model/serializer/adapter/attributes.rb +15 -0
  55. data/lib/active_model/serializer/adapter/base.rb +18 -0
  56. data/lib/active_model/serializer/adapter/json.rb +15 -0
  57. data/lib/active_model/serializer/adapter/json_api.rb +15 -0
  58. data/lib/active_model/serializer/adapter/null.rb +15 -0
  59. data/lib/active_model/serializer/array_serializer.rb +12 -0
  60. data/lib/active_model/serializer/association.rb +34 -0
  61. data/lib/active_model/serializer/attribute.rb +25 -0
  62. data/lib/active_model/serializer/belongs_to_reflection.rb +7 -0
  63. data/lib/active_model/serializer/collection_reflection.rb +7 -0
  64. data/lib/active_model/serializer/collection_serializer.rb +87 -0
  65. data/lib/active_model/serializer/concerns/associations.rb +102 -0
  66. data/lib/active_model/serializer/concerns/attributes.rb +82 -0
  67. data/lib/active_model/serializer/concerns/caching.rb +292 -0
  68. data/lib/active_model/serializer/concerns/configuration.rb +59 -0
  69. data/lib/active_model/serializer/concerns/links.rb +35 -0
  70. data/lib/active_model/serializer/concerns/meta.rb +29 -0
  71. data/lib/active_model/serializer/concerns/type.rb +25 -0
  72. data/lib/active_model/serializer/error_serializer.rb +14 -0
  73. data/lib/active_model/serializer/errors_serializer.rb +32 -0
  74. data/lib/active_model/serializer/field.rb +90 -0
  75. data/lib/active_model/serializer/fieldset.rb +31 -0
  76. data/lib/active_model/serializer/has_many_reflection.rb +7 -0
  77. data/lib/active_model/serializer/has_one_reflection.rb +7 -0
  78. data/lib/active_model/serializer/lint.rb +150 -0
  79. data/lib/active_model/serializer/null.rb +17 -0
  80. data/lib/active_model/serializer/reflection.rb +163 -0
  81. data/lib/active_model/serializer/singular_reflection.rb +7 -0
  82. data/lib/active_model/serializer/version.rb +5 -0
  83. data/lib/active_model_serializers.rb +53 -0
  84. data/lib/active_model_serializers/adapter.rb +98 -0
  85. data/lib/active_model_serializers/adapter/attributes.rb +13 -0
  86. data/lib/active_model_serializers/adapter/base.rb +83 -0
  87. data/lib/active_model_serializers/adapter/json.rb +21 -0
  88. data/lib/active_model_serializers/adapter/json_api.rb +517 -0
  89. data/lib/active_model_serializers/adapter/json_api/deserialization.rb +213 -0
  90. data/lib/active_model_serializers/adapter/json_api/error.rb +96 -0
  91. data/lib/active_model_serializers/adapter/json_api/jsonapi.rb +49 -0
  92. data/lib/active_model_serializers/adapter/json_api/link.rb +83 -0
  93. data/lib/active_model_serializers/adapter/json_api/meta.rb +37 -0
  94. data/lib/active_model_serializers/adapter/json_api/pagination_links.rb +69 -0
  95. data/lib/active_model_serializers/adapter/json_api/relationship.rb +63 -0
  96. data/lib/active_model_serializers/adapter/json_api/resource_identifier.rb +51 -0
  97. data/lib/active_model_serializers/adapter/null.rb +9 -0
  98. data/lib/active_model_serializers/callbacks.rb +55 -0
  99. data/lib/active_model_serializers/deprecate.rb +54 -0
  100. data/lib/active_model_serializers/deserialization.rb +15 -0
  101. data/lib/active_model_serializers/json_pointer.rb +14 -0
  102. data/lib/active_model_serializers/logging.rb +122 -0
  103. data/lib/active_model_serializers/lookup_chain.rb +80 -0
  104. data/lib/active_model_serializers/model.rb +71 -0
  105. data/lib/active_model_serializers/railtie.rb +48 -0
  106. data/lib/active_model_serializers/register_jsonapi_renderer.rb +78 -0
  107. data/lib/active_model_serializers/serializable_resource.rb +82 -0
  108. data/lib/active_model_serializers/serialization_context.rb +39 -0
  109. data/lib/active_model_serializers/test.rb +7 -0
  110. data/lib/active_model_serializers/test/schema.rb +138 -0
  111. data/lib/active_model_serializers/test/serializer.rb +125 -0
  112. data/lib/generators/rails/USAGE +6 -0
  113. data/lib/generators/rails/resource_override.rb +10 -0
  114. data/lib/generators/rails/serializer_generator.rb +36 -0
  115. data/lib/generators/rails/templates/serializer.rb.erb +15 -0
  116. data/lib/grape/active_model_serializers.rb +16 -0
  117. data/lib/grape/formatters/active_model_serializers.rb +32 -0
  118. data/lib/grape/helpers/active_model_serializers.rb +17 -0
  119. data/test/action_controller/adapter_selector_test.rb +53 -0
  120. data/test/action_controller/explicit_serializer_test.rb +135 -0
  121. data/test/action_controller/json/include_test.rb +246 -0
  122. data/test/action_controller/json_api/deserialization_test.rb +112 -0
  123. data/test/action_controller/json_api/errors_test.rb +40 -0
  124. data/test/action_controller/json_api/fields_test.rb +66 -0
  125. data/test/action_controller/json_api/linked_test.rb +202 -0
  126. data/test/action_controller/json_api/pagination_test.rb +116 -0
  127. data/test/action_controller/json_api/transform_test.rb +189 -0
  128. data/test/action_controller/lookup_proc_test.rb +49 -0
  129. data/test/action_controller/namespace_lookup_test.rb +232 -0
  130. data/test/action_controller/serialization_scope_name_test.rb +229 -0
  131. data/test/action_controller/serialization_test.rb +472 -0
  132. data/test/active_model_serializers/adapter_for_test.rb +208 -0
  133. data/test/active_model_serializers/json_pointer_test.rb +22 -0
  134. data/test/active_model_serializers/logging_test.rb +77 -0
  135. data/test/active_model_serializers/model_test.rb +69 -0
  136. data/test/active_model_serializers/railtie_test_isolated.rb +63 -0
  137. data/test/active_model_serializers/register_jsonapi_renderer_test_isolated.rb +161 -0
  138. data/test/active_model_serializers/serialization_context_test_isolated.rb +71 -0
  139. data/test/active_model_serializers/test/schema_test.rb +131 -0
  140. data/test/active_model_serializers/test/serializer_test.rb +62 -0
  141. data/test/active_record_test.rb +9 -0
  142. data/test/adapter/attributes_test.rb +43 -0
  143. data/test/adapter/deprecation_test.rb +100 -0
  144. data/test/adapter/json/belongs_to_test.rb +45 -0
  145. data/test/adapter/json/collection_test.rb +104 -0
  146. data/test/adapter/json/has_many_test.rb +45 -0
  147. data/test/adapter/json/transform_test.rb +93 -0
  148. data/test/adapter/json_api/belongs_to_test.rb +155 -0
  149. data/test/adapter/json_api/collection_test.rb +96 -0
  150. data/test/adapter/json_api/errors_test.rb +76 -0
  151. data/test/adapter/json_api/fields_test.rb +96 -0
  152. data/test/adapter/json_api/has_many_embed_ids_test.rb +43 -0
  153. data/test/adapter/json_api/has_many_explicit_serializer_test.rb +96 -0
  154. data/test/adapter/json_api/has_many_test.rb +165 -0
  155. data/test/adapter/json_api/has_one_test.rb +80 -0
  156. data/test/adapter/json_api/include_data_if_sideloaded_test.rb +168 -0
  157. data/test/adapter/json_api/json_api_test.rb +33 -0
  158. data/test/adapter/json_api/linked_test.rb +413 -0
  159. data/test/adapter/json_api/links_test.rb +95 -0
  160. data/test/adapter/json_api/pagination_links_test.rb +193 -0
  161. data/test/adapter/json_api/parse_test.rb +137 -0
  162. data/test/adapter/json_api/relationship_test.rb +397 -0
  163. data/test/adapter/json_api/resource_identifier_test.rb +110 -0
  164. data/test/adapter/json_api/resource_meta_test.rb +100 -0
  165. data/test/adapter/json_api/toplevel_jsonapi_test.rb +82 -0
  166. data/test/adapter/json_api/transform_test.rb +512 -0
  167. data/test/adapter/json_api/type_test.rb +61 -0
  168. data/test/adapter/json_test.rb +46 -0
  169. data/test/adapter/null_test.rb +22 -0
  170. data/test/adapter/polymorphic_test.rb +171 -0
  171. data/test/adapter_test.rb +67 -0
  172. data/test/array_serializer_test.rb +22 -0
  173. data/test/benchmark/app.rb +65 -0
  174. data/test/benchmark/benchmarking_support.rb +67 -0
  175. data/test/benchmark/bm_active_record.rb +81 -0
  176. data/test/benchmark/bm_adapter.rb +38 -0
  177. data/test/benchmark/bm_caching.rb +119 -0
  178. data/test/benchmark/bm_lookup_chain.rb +83 -0
  179. data/test/benchmark/bm_transform.rb +45 -0
  180. data/test/benchmark/config.ru +3 -0
  181. data/test/benchmark/controllers.rb +83 -0
  182. data/test/benchmark/fixtures.rb +219 -0
  183. data/test/cache_test.rb +595 -0
  184. data/test/collection_serializer_test.rb +123 -0
  185. data/test/fixtures/active_record.rb +113 -0
  186. data/test/fixtures/poro.rb +232 -0
  187. data/test/generators/scaffold_controller_generator_test.rb +24 -0
  188. data/test/generators/serializer_generator_test.rb +74 -0
  189. data/test/grape_test.rb +178 -0
  190. data/test/lint_test.rb +49 -0
  191. data/test/logger_test.rb +20 -0
  192. data/test/poro_test.rb +9 -0
  193. data/test/serializable_resource_test.rb +79 -0
  194. data/test/serializers/association_macros_test.rb +37 -0
  195. data/test/serializers/associations_test.rb +383 -0
  196. data/test/serializers/attribute_test.rb +153 -0
  197. data/test/serializers/attributes_test.rb +52 -0
  198. data/test/serializers/caching_configuration_test_isolated.rb +170 -0
  199. data/test/serializers/configuration_test.rb +32 -0
  200. data/test/serializers/fieldset_test.rb +14 -0
  201. data/test/serializers/meta_test.rb +202 -0
  202. data/test/serializers/options_test.rb +32 -0
  203. data/test/serializers/read_attribute_for_serialization_test.rb +79 -0
  204. data/test/serializers/root_test.rb +21 -0
  205. data/test/serializers/serialization_test.rb +55 -0
  206. data/test/serializers/serializer_for_test.rb +136 -0
  207. data/test/serializers/serializer_for_with_namespace_test.rb +88 -0
  208. data/test/support/custom_schemas/active_model_serializers/test/schema_test/my/index.json +6 -0
  209. data/test/support/isolated_unit.rb +82 -0
  210. data/test/support/rails5_shims.rb +53 -0
  211. data/test/support/rails_app.rb +36 -0
  212. data/test/support/schemas/active_model_serializers/test/schema_test/my/index.json +6 -0
  213. data/test/support/schemas/active_model_serializers/test/schema_test/my/show.json +6 -0
  214. data/test/support/schemas/custom/show.json +7 -0
  215. data/test/support/schemas/hyper_schema.json +93 -0
  216. data/test/support/schemas/render_using_json_api.json +43 -0
  217. data/test/support/schemas/simple_json_pointers.json +10 -0
  218. data/test/support/serialization_testing.rb +71 -0
  219. data/test/test_helper.rb +58 -0
  220. metadata +602 -0
@@ -0,0 +1,246 @@
1
+ require 'test_helper'
2
+
3
+ module ActionController
4
+ module Serialization
5
+ class Json
6
+ class IncludeTest < ActionController::TestCase
7
+ INCLUDE_STRING = 'posts.comments'.freeze
8
+ INCLUDE_HASH = { posts: :comments }.freeze
9
+ DEEP_INCLUDE = 'posts.comments.author'.freeze
10
+
11
+ class IncludeTestController < ActionController::Base
12
+ def setup_data
13
+ ActionController::Base.cache_store.clear
14
+
15
+ @author = Author.new(id: 1, name: 'Steve K.')
16
+
17
+ @post = Post.new(id: 42, title: 'New Post', body: 'Body')
18
+ @first_comment = Comment.new(id: 1, body: 'ZOMG A COMMENT')
19
+ @second_comment = Comment.new(id: 2, body: 'ZOMG ANOTHER COMMENT')
20
+
21
+ @post.comments = [@first_comment, @second_comment]
22
+ @post.author = @author
23
+
24
+ @first_comment.post = @post
25
+ @second_comment.post = @post
26
+
27
+ @blog = Blog.new(id: 1, name: 'My Blog!!')
28
+ @post.blog = @blog
29
+ @author.posts = [@post]
30
+
31
+ @first_comment.author = @author
32
+ @second_comment.author = @author
33
+ @author.comments = [@first_comment, @second_comment]
34
+ @author.roles = []
35
+ @author.bio = {}
36
+ end
37
+
38
+ def render_without_include
39
+ setup_data
40
+ render json: @author, adapter: :json
41
+ end
42
+
43
+ def render_resource_with_include_hash
44
+ setup_data
45
+ render json: @author, include: INCLUDE_HASH, adapter: :json
46
+ end
47
+
48
+ def render_resource_with_include_string
49
+ setup_data
50
+ render json: @author, include: INCLUDE_STRING, adapter: :json
51
+ end
52
+
53
+ def render_resource_with_deep_include
54
+ setup_data
55
+ render json: @author, include: DEEP_INCLUDE, adapter: :json
56
+ end
57
+
58
+ def render_without_recursive_relationships
59
+ # testing recursive includes ('**') can't have any cycles in the
60
+ # relationships, or we enter an infinite loop.
61
+ author = Author.new(id: 11, name: 'Jane Doe')
62
+ post = Post.new(id: 12, title: 'Hello World', body: 'My first post')
63
+ comment = Comment.new(id: 13, body: 'Commentary')
64
+ author.posts = [post]
65
+ post.comments = [comment]
66
+ render json: author
67
+ end
68
+ end
69
+
70
+ tests IncludeTestController
71
+
72
+ def test_render_without_include
73
+ get :render_without_include
74
+ response = JSON.parse(@response.body)
75
+ expected = {
76
+ 'author' => {
77
+ 'id' => 1,
78
+ 'name' => 'Steve K.',
79
+ 'posts' => [
80
+ {
81
+ 'id' => 42, 'title' => 'New Post', 'body' => 'Body'
82
+ }
83
+ ],
84
+ 'roles' => [],
85
+ 'bio' => {}
86
+ }
87
+ }
88
+
89
+ assert_equal(expected, response)
90
+ end
91
+
92
+ def test_render_resource_with_include_hash
93
+ get :render_resource_with_include_hash
94
+ response = JSON.parse(@response.body)
95
+
96
+ assert_equal(expected_include_response, response)
97
+ end
98
+
99
+ def test_render_resource_with_include_string
100
+ get :render_resource_with_include_string
101
+
102
+ response = JSON.parse(@response.body)
103
+
104
+ assert_equal(expected_include_response, response)
105
+ end
106
+
107
+ def test_render_resource_with_deep_include
108
+ get :render_resource_with_deep_include
109
+
110
+ response = JSON.parse(@response.body)
111
+
112
+ assert_equal(expected_deep_include_response, response)
113
+ end
114
+
115
+ def test_render_with_empty_default_includes
116
+ with_default_includes '' do
117
+ get :render_without_include
118
+ response = JSON.parse(@response.body)
119
+ expected = {
120
+ 'author' => {
121
+ 'id' => 1,
122
+ 'name' => 'Steve K.'
123
+ }
124
+ }
125
+ assert_equal(expected, response)
126
+ end
127
+ end
128
+
129
+ def test_render_with_recursive_default_includes
130
+ with_default_includes '**' do
131
+ get :render_without_recursive_relationships
132
+ response = JSON.parse(@response.body)
133
+
134
+ expected = {
135
+ 'id' => 11,
136
+ 'name' => 'Jane Doe',
137
+ 'roles' => nil,
138
+ 'bio' => nil,
139
+ 'posts' => [
140
+ {
141
+ 'id' => 12,
142
+ 'title' => 'Hello World',
143
+ 'body' => 'My first post',
144
+ 'comments' => [
145
+ {
146
+ 'id' => 13,
147
+ 'body' => 'Commentary',
148
+ 'post' => nil, # not set to avoid infinite recursion
149
+ 'author' => nil, # not set to avoid infinite recursion
150
+ }
151
+ ],
152
+ 'blog' => {
153
+ 'id' => 999,
154
+ 'name' => 'Custom blog',
155
+ 'writer' => nil,
156
+ 'articles' => nil
157
+ },
158
+ 'author' => nil # not set to avoid infinite recursion
159
+ }
160
+ ]
161
+ }
162
+ assert_equal(expected, response)
163
+ end
164
+ end
165
+
166
+ def test_render_with_includes_overrides_default_includes
167
+ with_default_includes '' do
168
+ get :render_resource_with_include_hash
169
+ response = JSON.parse(@response.body)
170
+
171
+ assert_equal(expected_include_response, response)
172
+ end
173
+ end
174
+
175
+ private
176
+
177
+ def expected_include_response
178
+ {
179
+ 'author' => {
180
+ 'id' => 1,
181
+ 'name' => 'Steve K.',
182
+ 'posts' => [
183
+ {
184
+ 'id' => 42, 'title' => 'New Post', 'body' => 'Body',
185
+ 'comments' => [
186
+ {
187
+ 'id' => 1, 'body' => 'ZOMG A COMMENT'
188
+ },
189
+ {
190
+ 'id' => 2, 'body' => 'ZOMG ANOTHER COMMENT'
191
+ }
192
+ ]
193
+ }
194
+ ]
195
+ }
196
+ }
197
+ end
198
+
199
+ def expected_deep_include_response
200
+ {
201
+ 'author' => {
202
+ 'id' => 1,
203
+ 'name' => 'Steve K.',
204
+ 'posts' => [
205
+ {
206
+ 'id' => 42, 'title' => 'New Post', 'body' => 'Body',
207
+ 'comments' => [
208
+ {
209
+ 'id' => 1, 'body' => 'ZOMG A COMMENT',
210
+ 'author' => {
211
+ 'id' => 1,
212
+ 'name' => 'Steve K.'
213
+ }
214
+ },
215
+ {
216
+ 'id' => 2, 'body' => 'ZOMG ANOTHER COMMENT',
217
+ 'author' => {
218
+ 'id' => 1,
219
+ 'name' => 'Steve K.'
220
+ }
221
+ }
222
+ ]
223
+ }
224
+ ]
225
+ }
226
+ }
227
+ end
228
+
229
+ def with_default_includes(include_directive)
230
+ original = ActiveModelSerializers.config.default_includes
231
+ ActiveModelSerializers.config.default_includes = include_directive
232
+ clear_include_directive_cache
233
+ yield
234
+ ensure
235
+ ActiveModelSerializers.config.default_includes = original
236
+ clear_include_directive_cache
237
+ end
238
+
239
+ def clear_include_directive_cache
240
+ ActiveModelSerializers
241
+ .instance_variable_set(:@default_include_directive, nil)
242
+ end
243
+ end
244
+ end
245
+ end
246
+ end
@@ -0,0 +1,112 @@
1
+ require 'test_helper'
2
+
3
+ module ActionController
4
+ module Serialization
5
+ class JsonApi
6
+ class DeserializationTest < ActionController::TestCase
7
+ class DeserializationTestController < ActionController::Base
8
+ def render_parsed_payload
9
+ parsed_hash = ActiveModelSerializers::Deserialization.jsonapi_parse(params)
10
+ render json: parsed_hash
11
+ end
12
+
13
+ def render_polymorphic_parsed_payload
14
+ parsed_hash = ActiveModelSerializers::Deserialization.jsonapi_parse(
15
+ params,
16
+ polymorphic: [:restriction_for, :restricted_to]
17
+ )
18
+ render json: parsed_hash
19
+ end
20
+ end
21
+
22
+ tests DeserializationTestController
23
+
24
+ def test_deserialization_of_relationship_only_object
25
+ hash = {
26
+ 'data' => {
27
+ 'type' => 'restraints',
28
+ 'relationships' => {
29
+ 'restriction_for' => {
30
+ 'data' => {
31
+ 'type' => 'discounts',
32
+ 'id' => '67'
33
+ }
34
+ },
35
+ 'restricted_to' => {
36
+ 'data' => nil
37
+ }
38
+ }
39
+ },
40
+ 'restraint' => {}
41
+ }
42
+
43
+ post :render_polymorphic_parsed_payload, params: hash
44
+
45
+ response = JSON.parse(@response.body)
46
+ expected = {
47
+ 'restriction_for_id' => '67',
48
+ 'restriction_for_type' => 'discounts',
49
+ 'restricted_to_id' => nil,
50
+ 'restricted_to_type' => nil
51
+ }
52
+
53
+ assert_equal(expected, response)
54
+ end
55
+
56
+ def test_deserialization
57
+ hash = {
58
+ 'data' => {
59
+ 'type' => 'photos',
60
+ 'id' => 'zorglub',
61
+ 'attributes' => {
62
+ 'title' => 'Ember Hamster',
63
+ 'src' => 'http://example.com/images/productivity.png',
64
+ 'image-width' => '200',
65
+ 'imageHeight' => '200',
66
+ 'ImageSize' => '1024'
67
+ },
68
+ 'relationships' => {
69
+ 'author' => {
70
+ 'data' => nil
71
+ },
72
+ 'photographer' => {
73
+ 'data' => { 'type' => 'people', 'id' => '9' }
74
+ },
75
+ 'comments' => {
76
+ 'data' => [
77
+ { 'type' => 'comments', 'id' => '1' },
78
+ { 'type' => 'comments', 'id' => '2' }
79
+ ]
80
+ },
81
+ 'related-images' => {
82
+ 'data' => [
83
+ { 'type' => 'image', 'id' => '7' },
84
+ { 'type' => 'image', 'id' => '8' }
85
+ ]
86
+ }
87
+ }
88
+ }
89
+ }
90
+
91
+ post :render_parsed_payload, params: hash
92
+
93
+ response = JSON.parse(@response.body)
94
+ expected = {
95
+ 'id' => 'zorglub',
96
+ 'title' => 'Ember Hamster',
97
+ 'src' => 'http://example.com/images/productivity.png',
98
+ 'image_width' => '200',
99
+ 'image_height' => '200',
100
+ 'image_size' => '1024',
101
+ 'author_id' => nil,
102
+ 'photographer_id' => '9',
103
+ 'comment_ids' => %w(1 2),
104
+ 'related_image_ids' => %w(7 8)
105
+ }
106
+
107
+ assert_equal(expected, response)
108
+ end
109
+ end
110
+ end
111
+ end
112
+ end
@@ -0,0 +1,40 @@
1
+ require 'test_helper'
2
+
3
+ module ActionController
4
+ module Serialization
5
+ class JsonApi
6
+ class ErrorsTest < ActionController::TestCase
7
+ def test_active_model_with_multiple_errors
8
+ get :render_resource_with_errors
9
+
10
+ expected_errors_object = {
11
+ errors: [
12
+ { source: { pointer: '/data/attributes/name' }, detail: 'cannot be nil' },
13
+ { source: { pointer: '/data/attributes/name' }, detail: 'must be longer' },
14
+ { source: { pointer: '/data/attributes/id' }, detail: 'must be a uuid' }
15
+ ]
16
+ }.to_json
17
+ assert_equal json_response_body.to_json, expected_errors_object
18
+ end
19
+
20
+ def json_response_body
21
+ JSON.load(@response.body)
22
+ end
23
+
24
+ class ErrorsTestController < ActionController::Base
25
+ def render_resource_with_errors
26
+ resource = Profile.new(name: 'Name 1',
27
+ description: 'Description 1',
28
+ comments: 'Comments 1')
29
+ resource.errors.add(:name, 'cannot be nil')
30
+ resource.errors.add(:name, 'must be longer')
31
+ resource.errors.add(:id, 'must be a uuid')
32
+ render json: resource, adapter: :json_api, serializer: ActiveModel::Serializer::ErrorSerializer
33
+ end
34
+ end
35
+
36
+ tests ErrorsTestController
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,66 @@
1
+ require 'test_helper'
2
+
3
+ module ActionController
4
+ module Serialization
5
+ class JsonApi
6
+ class FieldsTest < ActionController::TestCase
7
+ class FieldsTestController < ActionController::Base
8
+ class AuthorWithName < Author
9
+ attributes :first_name, :last_name
10
+ end
11
+ class AuthorWithNameSerializer < AuthorSerializer
12
+ type 'authors'
13
+ end
14
+ class PostWithPublishAt < Post
15
+ attributes :publish_at
16
+ end
17
+ class PostWithPublishAtSerializer < ActiveModel::Serializer
18
+ type 'posts'
19
+ attributes :title, :body, :publish_at
20
+ belongs_to :author
21
+ has_many :comments
22
+ end
23
+
24
+ def setup_post
25
+ ActionController::Base.cache_store.clear
26
+ @author = AuthorWithName.new(id: 1, first_name: 'Bob', last_name: 'Jones')
27
+ @comment1 = Comment.new(id: 7, body: 'cool', author: @author)
28
+ @comment2 = Comment.new(id: 12, body: 'awesome', author: @author)
29
+ @post = PostWithPublishAt.new(id: 1337, title: 'Title 1', body: 'Body 1',
30
+ author: @author, comments: [@comment1, @comment2],
31
+ publish_at: '2020-03-16T03:55:25.291Z')
32
+ @comment1.post = @post
33
+ @comment2.post = @post
34
+ end
35
+
36
+ def render_fields_works_on_relationships
37
+ setup_post
38
+ render json: @post, serializer: PostWithPublishAtSerializer, adapter: :json_api, fields: { posts: [:author] }
39
+ end
40
+ end
41
+
42
+ tests FieldsTestController
43
+
44
+ test 'fields works on relationships' do
45
+ get :render_fields_works_on_relationships
46
+ response = JSON.parse(@response.body)
47
+ expected = {
48
+ 'data' => {
49
+ 'id' => '1337',
50
+ 'type' => 'posts',
51
+ 'relationships' => {
52
+ 'author' => {
53
+ 'data' => {
54
+ 'id' => '1',
55
+ 'type' => 'authors'
56
+ }
57
+ }
58
+ }
59
+ }
60
+ }
61
+ assert_equal expected, response
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end