active_model_serializers 0.10.0.rc4 → 0.10.0.rc5

Sign up to get free protection for your applications and to get access to all the features.
Files changed (179) hide show
  1. checksums.yaml +4 -4
  2. data/.github/ISSUE_TEMPLATE.md +29 -0
  3. data/.github/PULL_REQUEST_TEMPLATE.md +15 -0
  4. data/.gitignore +1 -0
  5. data/.rubocop.yml +19 -1
  6. data/.rubocop_todo.yml +30 -103
  7. data/.simplecov +0 -1
  8. data/.travis.yml +20 -8
  9. data/CHANGELOG.md +89 -5
  10. data/CONTRIBUTING.md +54 -179
  11. data/Gemfile +7 -2
  12. data/{LICENSE.txt → MIT-LICENSE} +0 -0
  13. data/README.md +27 -5
  14. data/Rakefile +44 -16
  15. data/active_model_serializers.gemspec +9 -1
  16. data/appveyor.yml +1 -0
  17. data/bin/bench +171 -0
  18. data/bin/bench_regression +316 -0
  19. data/bin/serve_benchmark +39 -0
  20. data/docs/ARCHITECTURE.md +13 -7
  21. data/docs/README.md +5 -1
  22. data/docs/STYLE.md +58 -0
  23. data/docs/general/adapters.md +99 -16
  24. data/docs/general/configuration_options.md +87 -14
  25. data/docs/general/deserialization.md +100 -0
  26. data/docs/general/getting_started.md +35 -0
  27. data/docs/general/instrumentation.md +1 -1
  28. data/docs/general/key_transforms.md +40 -0
  29. data/docs/general/rendering.md +115 -13
  30. data/docs/general/serializers.md +138 -6
  31. data/docs/howto/add_pagination_links.md +36 -18
  32. data/docs/howto/outside_controller_use.md +4 -4
  33. data/docs/howto/passing_arbitrary_options.md +27 -0
  34. data/docs/jsonapi/errors.md +56 -0
  35. data/docs/jsonapi/schema.md +29 -18
  36. data/docs/rfcs/0000-namespace.md +106 -0
  37. data/docs/rfcs/template.md +15 -0
  38. data/lib/action_controller/serialization.rb +10 -19
  39. data/lib/active_model/serializable_resource.rb +4 -65
  40. data/lib/active_model/serializer.rb +73 -18
  41. data/lib/active_model/serializer/adapter.rb +15 -82
  42. data/lib/active_model/serializer/adapter/attributes.rb +5 -56
  43. data/lib/active_model/serializer/adapter/base.rb +5 -47
  44. data/lib/active_model/serializer/adapter/json.rb +6 -12
  45. data/lib/active_model/serializer/adapter/json_api.rb +5 -213
  46. data/lib/active_model/serializer/adapter/null.rb +7 -3
  47. data/lib/active_model/serializer/array_serializer.rb +3 -3
  48. data/lib/active_model/serializer/association.rb +4 -5
  49. data/lib/active_model/serializer/attributes.rb +1 -1
  50. data/lib/active_model/serializer/caching.rb +56 -5
  51. data/lib/active_model/serializer/collection_serializer.rb +30 -13
  52. data/lib/active_model/serializer/configuration.rb +7 -0
  53. data/lib/active_model/serializer/error_serializer.rb +10 -0
  54. data/lib/active_model/serializer/errors_serializer.rb +27 -0
  55. data/lib/active_model/serializer/links.rb +4 -2
  56. data/lib/active_model/serializer/lint.rb +14 -0
  57. data/lib/active_model/serializer/meta.rb +29 -0
  58. data/lib/active_model/serializer/null.rb +17 -0
  59. data/lib/active_model/serializer/reflection.rb +57 -1
  60. data/lib/active_model/serializer/type.rb +1 -1
  61. data/lib/active_model/serializer/version.rb +1 -1
  62. data/lib/active_model_serializers.rb +17 -0
  63. data/lib/active_model_serializers/adapter.rb +92 -0
  64. data/lib/active_model_serializers/adapter/attributes.rb +94 -0
  65. data/lib/active_model_serializers/adapter/base.rb +90 -0
  66. data/lib/active_model_serializers/adapter/json.rb +11 -0
  67. data/lib/active_model_serializers/adapter/json_api.rb +513 -0
  68. data/lib/active_model_serializers/adapter/json_api/deserialization.rb +213 -0
  69. data/lib/active_model_serializers/adapter/json_api/error.rb +96 -0
  70. data/lib/active_model_serializers/adapter/json_api/jsonapi.rb +49 -0
  71. data/lib/active_model_serializers/adapter/json_api/link.rb +83 -0
  72. data/lib/active_model_serializers/adapter/json_api/meta.rb +37 -0
  73. data/lib/active_model_serializers/adapter/json_api/pagination_links.rb +57 -0
  74. data/lib/active_model_serializers/adapter/json_api/relationship.rb +52 -0
  75. data/lib/active_model_serializers/adapter/json_api/resource_identifier.rb +37 -0
  76. data/lib/active_model_serializers/adapter/null.rb +10 -0
  77. data/lib/active_model_serializers/cached_serializer.rb +87 -0
  78. data/lib/active_model_serializers/callbacks.rb +1 -1
  79. data/lib/active_model_serializers/deprecate.rb +55 -0
  80. data/lib/active_model_serializers/deserialization.rb +2 -2
  81. data/lib/active_model_serializers/fragment_cache.rb +118 -0
  82. data/lib/active_model_serializers/json_pointer.rb +14 -0
  83. data/lib/active_model_serializers/key_transform.rb +70 -0
  84. data/lib/active_model_serializers/logging.rb +4 -1
  85. data/lib/active_model_serializers/model.rb +11 -1
  86. data/lib/active_model_serializers/railtie.rb +9 -1
  87. data/lib/active_model_serializers/register_jsonapi_renderer.rb +64 -0
  88. data/lib/active_model_serializers/serializable_resource.rb +81 -0
  89. data/lib/active_model_serializers/serialization_context.rb +24 -2
  90. data/lib/active_model_serializers/test/schema.rb +2 -2
  91. data/lib/grape/formatters/active_model_serializers.rb +1 -1
  92. data/test/action_controller/adapter_selector_test.rb +1 -1
  93. data/test/action_controller/json_api/deserialization_test.rb +56 -3
  94. data/test/action_controller/json_api/errors_test.rb +41 -0
  95. data/test/action_controller/json_api/linked_test.rb +10 -9
  96. data/test/action_controller/json_api/pagination_test.rb +2 -2
  97. data/test/action_controller/json_api/transform_test.rb +180 -0
  98. data/test/action_controller/serialization_scope_name_test.rb +201 -35
  99. data/test/action_controller/serialization_test.rb +39 -7
  100. data/test/active_model_serializers/adapter_for_test.rb +208 -0
  101. data/test/active_model_serializers/cached_serializer_test.rb +80 -0
  102. data/test/active_model_serializers/fragment_cache_test.rb +34 -0
  103. data/test/active_model_serializers/json_pointer_test.rb +20 -0
  104. data/test/active_model_serializers/key_transform_test.rb +263 -0
  105. data/test/active_model_serializers/logging_test.rb +8 -8
  106. data/test/active_model_serializers/railtie_test_isolated.rb +6 -0
  107. data/test/active_model_serializers/serialization_context_test_isolated.rb +58 -0
  108. data/test/adapter/deprecation_test.rb +100 -0
  109. data/test/adapter/json/belongs_to_test.rb +32 -34
  110. data/test/adapter/json/collection_test.rb +73 -75
  111. data/test/adapter/json/has_many_test.rb +36 -38
  112. data/test/adapter/json/transform_test.rb +93 -0
  113. data/test/adapter/json_api/belongs_to_test.rb +127 -129
  114. data/test/adapter/json_api/collection_test.rb +80 -82
  115. data/test/adapter/json_api/errors_test.rb +78 -0
  116. data/test/adapter/json_api/fields_test.rb +68 -70
  117. data/test/adapter/json_api/has_many_embed_ids_test.rb +32 -34
  118. data/test/adapter/json_api/has_many_explicit_serializer_test.rb +75 -77
  119. data/test/adapter/json_api/has_many_test.rb +121 -123
  120. data/test/adapter/json_api/has_one_test.rb +59 -61
  121. data/test/adapter/json_api/json_api_test.rb +28 -30
  122. data/test/adapter/json_api/linked_test.rb +319 -321
  123. data/test/adapter/json_api/links_test.rb +75 -50
  124. data/test/adapter/json_api/pagination_links_test.rb +115 -82
  125. data/test/adapter/json_api/parse_test.rb +114 -116
  126. data/test/adapter/json_api/relationship_test.rb +161 -0
  127. data/test/adapter/json_api/relationships_test.rb +199 -0
  128. data/test/adapter/json_api/resource_identifier_test.rb +85 -0
  129. data/test/adapter/json_api/resource_meta_test.rb +100 -0
  130. data/test/adapter/json_api/toplevel_jsonapi_test.rb +61 -63
  131. data/test/adapter/json_api/transform_test.rb +500 -0
  132. data/test/adapter/json_api/type_test.rb +61 -0
  133. data/test/adapter/json_test.rb +35 -37
  134. data/test/adapter/null_test.rb +13 -15
  135. data/test/adapter/polymorphic_test.rb +72 -0
  136. data/test/adapter_test.rb +27 -29
  137. data/test/array_serializer_test.rb +7 -8
  138. data/test/benchmark/app.rb +65 -0
  139. data/test/benchmark/benchmarking_support.rb +67 -0
  140. data/test/benchmark/bm_caching.rb +117 -0
  141. data/test/benchmark/bm_transform.rb +34 -0
  142. data/test/benchmark/config.ru +3 -0
  143. data/test/benchmark/controllers.rb +77 -0
  144. data/test/benchmark/fixtures.rb +167 -0
  145. data/test/cache_test.rb +388 -0
  146. data/test/collection_serializer_test.rb +10 -0
  147. data/test/fixtures/active_record.rb +12 -0
  148. data/test/fixtures/poro.rb +28 -3
  149. data/test/grape_test.rb +5 -5
  150. data/test/lint_test.rb +9 -0
  151. data/test/serializable_resource_test.rb +59 -3
  152. data/test/serializers/associations_test.rb +8 -8
  153. data/test/serializers/attribute_test.rb +7 -7
  154. data/test/serializers/caching_configuration_test_isolated.rb +170 -0
  155. data/test/serializers/meta_test.rb +74 -6
  156. data/test/serializers/read_attribute_for_serialization_test.rb +79 -0
  157. data/test/serializers/serialization_test.rb +55 -0
  158. data/test/support/isolated_unit.rb +3 -0
  159. data/test/support/rails5_shims.rb +26 -8
  160. data/test/support/rails_app.rb +38 -18
  161. data/test/support/serialization_testing.rb +5 -5
  162. data/test/test_helper.rb +6 -10
  163. metadata +132 -37
  164. data/docs/DESIGN.textile +7 -1
  165. data/lib/active_model/serializer/adapter/cached_serializer.rb +0 -45
  166. data/lib/active_model/serializer/adapter/fragment_cache.rb +0 -111
  167. data/lib/active_model/serializer/adapter/json/fragment_cache.rb +0 -13
  168. data/lib/active_model/serializer/adapter/json_api/deserialization.rb +0 -207
  169. data/lib/active_model/serializer/adapter/json_api/fragment_cache.rb +0 -21
  170. data/lib/active_model/serializer/adapter/json_api/link.rb +0 -44
  171. data/lib/active_model/serializer/adapter/json_api/pagination_links.rb +0 -58
  172. data/test/active_model_serializers/serialization_context_test.rb +0 -18
  173. data/test/adapter/fragment_cache_test.rb +0 -38
  174. data/test/adapter/json_api/resource_type_config_test.rb +0 -71
  175. data/test/serializers/adapter_for_test.rb +0 -166
  176. data/test/serializers/cache_test.rb +0 -209
  177. data/test/support/simplecov.rb +0 -6
  178. data/test/support/stream_capture.rb +0 -50
  179. data/test/support/test_case.rb +0 -19
@@ -1,18 +0,0 @@
1
- require 'test_helper'
2
-
3
- class ActiveModelSerializers::SerializationContextTest < ActiveSupport::TestCase
4
- def create_context
5
- request = Minitest::Mock.new
6
- request.expect(:original_url, 'original_url')
7
- request.expect(:query_parameters, 'query_parameters')
8
-
9
- ActiveModelSerializers::SerializationContext.new(request)
10
- end
11
-
12
- def test_create_context_with_request_url_and_query_parameters
13
- context = create_context
14
-
15
- assert_equal context.request_url, 'original_url'
16
- assert_equal context.query_parameters, 'query_parameters'
17
- end
18
- end
@@ -1,38 +0,0 @@
1
- require 'test_helper'
2
- module ActiveModel
3
- class Serializer
4
- module Adapter
5
- class FragmentCacheTest < ActiveSupport::TestCase
6
- def setup
7
- super
8
- @spam = Spam::UnrelatedLink.new(id: 'spam-id-1')
9
- @author = Author.new(name: 'Joao M. D. Moura')
10
- @role = Role.new(name: 'Great Author', description: nil)
11
- @role.author = [@author]
12
- @role_serializer = RoleSerializer.new(@role)
13
- @spam_serializer = Spam::UnrelatedLinkSerializer.new(@spam)
14
- @role_hash = FragmentCache.new(RoleSerializer.adapter.new(@role_serializer), @role_serializer, {})
15
- @spam_hash = FragmentCache.new(Spam::UnrelatedLinkSerializer.adapter.new(@spam_serializer), @spam_serializer, {})
16
- end
17
-
18
- def test_fragment_fetch_with_virtual_attributes
19
- expected_result = {
20
- id: @role.id,
21
- description: @role.description,
22
- slug: "#{@role.name}-#{@role.id}",
23
- name: @role.name
24
- }
25
- assert_equal(@role_hash.fetch, expected_result)
26
- end
27
-
28
- def test_fragment_fetch_with_namespaced_object
29
- expected_result = {
30
- id: @spam.id
31
- }
32
- assert_equal(@spam_hash.fetch, expected_result)
33
- end
34
- end
35
- end
36
- end
37
- end
38
-
@@ -1,71 +0,0 @@
1
- require 'test_helper'
2
-
3
- module ActiveModel
4
- class Serializer
5
- module Adapter
6
- class JsonApi
7
- class ResourceTypeConfigTest < ActiveSupport::TestCase
8
- class ProfileTypeSerializer < ActiveModel::Serializer
9
- attributes :name
10
- type 'profile'
11
- end
12
-
13
- def setup
14
- @author = Author.new(id: 1, name: 'Steve K.')
15
- @author.bio = nil
16
- @author.roles = []
17
- @blog = Blog.new(id: 23, name: 'AMS Blog')
18
- @post = Post.new(id: 42, title: 'New Post', body: 'Body')
19
- @anonymous_post = Post.new(id: 43, title: 'Hello!!', body: 'Hello, world!!')
20
- @comment = Comment.new(id: 1, body: 'ZOMG A COMMENT')
21
- @post.comments = [@comment]
22
- @post.blog = @blog
23
- @anonymous_post.comments = []
24
- @anonymous_post.blog = nil
25
- @comment.post = @post
26
- @comment.author = nil
27
- @post.author = @author
28
- @anonymous_post.author = nil
29
- @blog = Blog.new(id: 1, name: 'My Blog!!')
30
- @blog.writer = @author
31
- @blog.articles = [@post, @anonymous_post]
32
- @author.posts = []
33
- end
34
-
35
- def with_jsonapi_resource_type type
36
- old_type = ActiveModelSerializers.config.jsonapi_resource_type
37
- ActiveModelSerializers.config.jsonapi_resource_type = type
38
- yield
39
- ensure
40
- ActiveModelSerializers.config.jsonapi_resource_type = old_type
41
- end
42
-
43
- def test_config_plural
44
- with_jsonapi_resource_type :plural do
45
- hash = serializable(@comment, adapter: :json_api).serializable_hash
46
- assert_equal('comments', hash[:data][:type])
47
- end
48
- end
49
-
50
- def test_config_singular
51
- with_jsonapi_resource_type :singular do
52
- hash = serializable(@comment, adapter: :json_api).serializable_hash
53
- assert_equal('comment', hash[:data][:type])
54
- end
55
- end
56
-
57
- def test_explicit_type_value
58
- hash = serializable(@author, serializer: ProfileTypeSerializer, adapter: :json_api).serializable_hash
59
- assert_equal('profile', hash.fetch(:data).fetch(:type))
60
- end
61
-
62
- private
63
-
64
- def serializable(resource, options = {})
65
- ActiveModel::SerializableResource.new(resource, options)
66
- end
67
- end
68
- end
69
- end
70
- end
71
- end
@@ -1,166 +0,0 @@
1
- module ActiveModel
2
- class Serializer
3
- class AdapterForTest < ActiveSupport::TestCase
4
- UnknownAdapterError = ::ActiveModel::Serializer::Adapter::UnknownAdapterError
5
-
6
- def setup
7
- @previous_adapter = ActiveModelSerializers.config.adapter
8
- end
9
-
10
- def teardown
11
- ActiveModelSerializers.config.adapter = @previous_adapter
12
- end
13
-
14
- def test_returns_default_adapter
15
- adapter = ActiveModel::Serializer.adapter
16
- assert_equal ActiveModel::Serializer::Adapter::Attributes, adapter
17
- end
18
-
19
- def test_overwrite_adapter_with_symbol
20
- ActiveModelSerializers.config.adapter = :null
21
-
22
- adapter = ActiveModel::Serializer.adapter
23
- assert_equal ActiveModel::Serializer::Adapter::Null, adapter
24
- ensure
25
- ActiveModelSerializers.config.adapter = @previous_adapter
26
- end
27
-
28
- def test_overwrite_adapter_with_class
29
- ActiveModelSerializers.config.adapter = ActiveModel::Serializer::Adapter::Null
30
-
31
- adapter = ActiveModel::Serializer.adapter
32
- assert_equal ActiveModel::Serializer::Adapter::Null, adapter
33
- end
34
-
35
- def test_raises_exception_if_invalid_symbol_given
36
- ActiveModelSerializers.config.adapter = :unknown
37
-
38
- assert_raises UnknownAdapterError do
39
- ActiveModel::Serializer.adapter
40
- end
41
- end
42
-
43
- def test_raises_exception_if_it_does_not_know_hot_to_infer_adapter
44
- ActiveModelSerializers.config.adapter = 42
45
-
46
- assert_raises UnknownAdapterError do
47
- ActiveModel::Serializer.adapter
48
- end
49
- end
50
-
51
- def test_adapter_class_for_known_adapter
52
- klass = ActiveModel::Serializer::Adapter.adapter_class(:json_api)
53
- assert_equal ActiveModel::Serializer::Adapter::JsonApi, klass
54
- end
55
-
56
- def test_adapter_class_for_unknown_adapter
57
- assert_raises UnknownAdapterError do
58
- ActiveModel::Serializer::Adapter.adapter_class(:json_simple)
59
- end
60
- end
61
-
62
- def test_adapter_map
63
- expected_adapter_map = {
64
- 'null'.freeze => ActiveModel::Serializer::Adapter::Null,
65
- 'json'.freeze => ActiveModel::Serializer::Adapter::Json,
66
- 'attributes'.freeze => ActiveModel::Serializer::Adapter::Attributes,
67
- 'json_api'.freeze => ActiveModel::Serializer::Adapter::JsonApi
68
- }
69
- actual = ActiveModel::Serializer::Adapter.adapter_map
70
- assert_equal actual, expected_adapter_map
71
- end
72
-
73
- def test_adapters
74
- assert_equal ActiveModel::Serializer::Adapter.adapters.sort, [
75
- 'attributes'.freeze,
76
- 'json'.freeze,
77
- 'json_api'.freeze,
78
- 'null'.freeze
79
- ]
80
- end
81
-
82
- def test_lookup_adapter_by_string_name
83
- assert_equal ActiveModel::Serializer::Adapter.lookup('json'.freeze), ActiveModel::Serializer::Adapter::Json
84
- end
85
-
86
- def test_lookup_adapter_by_symbol_name
87
- assert_equal ActiveModel::Serializer::Adapter.lookup(:json), ActiveModel::Serializer::Adapter::Json
88
- end
89
-
90
- def test_lookup_adapter_by_class
91
- klass = ActiveModel::Serializer::Adapter::Json
92
- assert_equal ActiveModel::Serializer::Adapter.lookup(klass), klass
93
- end
94
-
95
- def test_lookup_adapter_from_environment_registers_adapter
96
- ActiveModel::Serializer::Adapter.const_set(:AdapterFromEnvironment, Class.new)
97
- klass = ::ActiveModel::Serializer::Adapter::AdapterFromEnvironment
98
- name = 'adapter_from_environment'.freeze
99
- assert_equal ActiveModel::Serializer::Adapter.lookup(name), klass
100
- assert ActiveModel::Serializer::Adapter.adapters.include?(name)
101
- ensure
102
- ActiveModel::Serializer::Adapter.adapter_map.delete(name)
103
- ActiveModel::Serializer::Adapter.send(:remove_const, :AdapterFromEnvironment)
104
- end
105
-
106
- def test_lookup_adapter_for_unknown_name
107
- assert_raises UnknownAdapterError do
108
- ActiveModel::Serializer::Adapter.lookup(:json_simple)
109
- end
110
- end
111
-
112
- def test_adapter
113
- assert_equal ActiveModelSerializers.config.adapter, :attributes
114
- assert_equal ActiveModel::Serializer.adapter, ActiveModel::Serializer::Adapter::Attributes
115
- end
116
-
117
- def test_register_adapter
118
- new_adapter_name = :foo
119
- new_adapter_klass = Class.new
120
- ActiveModel::Serializer::Adapter.register(new_adapter_name, new_adapter_klass)
121
- assert ActiveModel::Serializer::Adapter.adapters.include?('foo'.freeze)
122
- assert ActiveModel::Serializer::Adapter.lookup(:foo), new_adapter_klass
123
- ensure
124
- ActiveModel::Serializer::Adapter.adapter_map.delete(new_adapter_name.to_s)
125
- end
126
-
127
- def test_inherited_adapter_hooks_register_adapter
128
- Object.const_set(:MyAdapter, Class.new)
129
- my_adapter = MyAdapter
130
- ActiveModel::Serializer::Adapter::Base.inherited(my_adapter)
131
- assert_equal ActiveModel::Serializer::Adapter.lookup(:my_adapter), my_adapter
132
- ensure
133
- ActiveModel::Serializer::Adapter.adapter_map.delete('my_adapter'.freeze)
134
- Object.send(:remove_const, :MyAdapter)
135
- end
136
-
137
- def test_inherited_adapter_hooks_register_namespaced_adapter
138
- Object.const_set(:MyNamespace, Module.new)
139
- MyNamespace.const_set(:MyAdapter, Class.new)
140
- my_adapter = MyNamespace::MyAdapter
141
- ActiveModel::Serializer::Adapter::Base.inherited(my_adapter)
142
- assert_equal ActiveModel::Serializer::Adapter.lookup(:'my_namespace/my_adapter'), my_adapter
143
- ensure
144
- ActiveModel::Serializer::Adapter.adapter_map.delete('my_namespace/my_adapter'.freeze)
145
- MyNamespace.send(:remove_const, :MyAdapter)
146
- Object.send(:remove_const, :MyNamespace)
147
- end
148
-
149
- def test_inherited_adapter_hooks_register_subclass_of_registered_adapter
150
- Object.const_set(:MyAdapter, Class.new)
151
- my_adapter = MyAdapter
152
- Object.const_set(:MySubclassedAdapter, Class.new(MyAdapter))
153
- my_subclassed_adapter = MySubclassedAdapter
154
- ActiveModel::Serializer::Adapter::Base.inherited(my_adapter)
155
- ActiveModel::Serializer::Adapter::Base.inherited(my_subclassed_adapter)
156
- assert_equal ActiveModel::Serializer::Adapter.lookup(:my_adapter), my_adapter
157
- assert_equal ActiveModel::Serializer::Adapter.lookup(:my_subclassed_adapter), my_subclassed_adapter
158
- ensure
159
- ActiveModel::Serializer::Adapter.adapter_map.delete('my_adapter'.freeze)
160
- ActiveModel::Serializer::Adapter.adapter_map.delete('my_subclassed_adapter'.freeze)
161
- Object.send(:remove_const, :MyAdapter)
162
- Object.send(:remove_const, :MySubclassedAdapter)
163
- end
164
- end
165
- end
166
- end
@@ -1,209 +0,0 @@
1
- require 'test_helper'
2
- require 'tmpdir'
3
- require 'tempfile'
4
- module ActiveModel
5
- class Serializer
6
- class CacheTest < ActiveSupport::TestCase
7
- include ActiveSupport::Testing::Stream
8
-
9
- def setup
10
- ActionController::Base.cache_store.clear
11
- @comment = Comment.new(id: 1, body: 'ZOMG A COMMENT')
12
- @post = Post.new(title: 'New Post', body: 'Body')
13
- @bio = Bio.new(id: 1, content: 'AMS Contributor')
14
- @author = Author.new(name: 'Joao M. D. Moura')
15
- @blog = Blog.new(id: 999, name: 'Custom blog', writer: @author, articles: [])
16
- @role = Role.new(name: 'Great Author')
17
- @location = Location.new(lat: '-23.550520', lng: '-46.633309')
18
- @place = Place.new(name: 'Amazing Place')
19
- @author.posts = [@post]
20
- @author.roles = [@role]
21
- @role.author = @author
22
- @author.bio = @bio
23
- @bio.author = @author
24
- @post.comments = [@comment]
25
- @post.author = @author
26
- @comment.post = @post
27
- @comment.author = @author
28
- @post.blog = @blog
29
- @location.place = @place
30
-
31
- @location_serializer = LocationSerializer.new(@location)
32
- @bio_serializer = BioSerializer.new(@bio)
33
- @role_serializer = RoleSerializer.new(@role)
34
- @post_serializer = PostSerializer.new(@post)
35
- @author_serializer = AuthorSerializer.new(@author)
36
- @comment_serializer = CommentSerializer.new(@comment)
37
- @blog_serializer = BlogSerializer.new(@blog)
38
- end
39
-
40
- def test_inherited_cache_configuration
41
- inherited_serializer = Class.new(PostSerializer)
42
-
43
- assert_equal PostSerializer._cache_key, inherited_serializer._cache_key
44
- assert_equal PostSerializer._cache_options, inherited_serializer._cache_options
45
- end
46
-
47
- def test_override_cache_configuration
48
- inherited_serializer = Class.new(PostSerializer) do
49
- cache key: 'new-key'
50
- end
51
-
52
- assert_equal PostSerializer._cache_key, 'post'
53
- assert_equal inherited_serializer._cache_key, 'new-key'
54
- end
55
-
56
- def test_cache_definition
57
- assert_equal(ActionController::Base.cache_store, @post_serializer.class._cache)
58
- assert_equal(ActionController::Base.cache_store, @author_serializer.class._cache)
59
- assert_equal(ActionController::Base.cache_store, @comment_serializer.class._cache)
60
- end
61
-
62
- def test_cache_key_definition
63
- assert_equal('post', @post_serializer.class._cache_key)
64
- assert_equal('writer', @author_serializer.class._cache_key)
65
- assert_equal(nil, @comment_serializer.class._cache_key)
66
- end
67
-
68
- def test_cache_key_interpolation_with_updated_at
69
- render_object_with_cache(@author)
70
- assert_equal(nil, ActionController::Base.cache_store.fetch(@author.cache_key))
71
- assert_equal(@author_serializer.attributes.to_json, ActionController::Base.cache_store.fetch("#{@author_serializer.class._cache_key}/#{@author_serializer.object.id}-#{@author_serializer.object.updated_at.strftime("%Y%m%d%H%M%S%9N")}").to_json)
72
- end
73
-
74
- def test_default_cache_key_fallback
75
- render_object_with_cache(@comment)
76
- assert_equal(@comment_serializer.attributes.to_json, ActionController::Base.cache_store.fetch(@comment.cache_key).to_json)
77
- end
78
-
79
- def test_cache_options_definition
80
- assert_equal({ expires_in: 0.1, skip_digest: true }, @post_serializer.class._cache_options)
81
- assert_equal(nil, @blog_serializer.class._cache_options)
82
- assert_equal({ expires_in: 1.day, skip_digest: true }, @comment_serializer.class._cache_options)
83
- end
84
-
85
- def test_fragment_cache_definition
86
- assert_equal([:name], @role_serializer.class._cache_only)
87
- assert_equal([:content], @bio_serializer.class._cache_except)
88
- end
89
-
90
- def test_associations_separately_cache
91
- ActionController::Base.cache_store.clear
92
- assert_equal(nil, ActionController::Base.cache_store.fetch(@post.cache_key))
93
- assert_equal(nil, ActionController::Base.cache_store.fetch(@comment.cache_key))
94
-
95
- Timecop.freeze(Time.now) do
96
- render_object_with_cache(@post)
97
-
98
- assert_equal(@post_serializer.attributes, ActionController::Base.cache_store.fetch(@post.cache_key))
99
- assert_equal(@comment_serializer.attributes, ActionController::Base.cache_store.fetch(@comment.cache_key))
100
- end
101
- end
102
-
103
- def test_associations_cache_when_updated
104
- # Clean the Cache
105
- ActionController::Base.cache_store.clear
106
-
107
- Timecop.freeze(Time.now) do
108
- # Generate a new Cache of Post object and each objects related to it.
109
- render_object_with_cache(@post)
110
-
111
- # Check if it cached the objects separately
112
- assert_equal(@post_serializer.attributes, ActionController::Base.cache_store.fetch(@post.cache_key))
113
- assert_equal(@comment_serializer.attributes, ActionController::Base.cache_store.fetch(@comment.cache_key))
114
-
115
- # Simulating update on comments relationship with Post
116
- new_comment = Comment.new(id: 2, body: 'ZOMG A NEW COMMENT')
117
- new_comment_serializer = CommentSerializer.new(new_comment)
118
- @post.comments = [new_comment]
119
-
120
- # Ask for the serialized object
121
- render_object_with_cache(@post)
122
-
123
- # Check if the the new comment was cached
124
- assert_equal(new_comment_serializer.attributes, ActionController::Base.cache_store.fetch(new_comment.cache_key))
125
- assert_equal(@post_serializer.attributes, ActionController::Base.cache_store.fetch(@post.cache_key))
126
- end
127
- end
128
-
129
- def test_fragment_fetch_with_virtual_associations
130
- expected_result = {
131
- id: @location.id,
132
- lat: @location.lat,
133
- lng: @location.lng,
134
- place: 'Nowhere'
135
- }
136
-
137
- hash = render_object_with_cache(@location)
138
-
139
- assert_equal(hash, expected_result)
140
- assert_equal({ place: 'Nowhere' }, ActionController::Base.cache_store.fetch(@location.cache_key))
141
- end
142
-
143
- def test_uses_file_digest_in_cache_key
144
- render_object_with_cache(@blog)
145
- assert_equal(@blog_serializer.attributes, ActionController::Base.cache_store.fetch(@blog.cache_key_with_digest))
146
- end
147
-
148
- def test_cache_digest_definition
149
- assert_equal(::Model::FILE_DIGEST, @post_serializer.class._cache_digest)
150
- end
151
-
152
- def test_serializer_file_path_on_nix
153
- path = '/Users/git/emberjs/ember-crm-backend/app/serializers/lead_serializer.rb'
154
- caller_line = "#{path}:1:in `<top (required)>'"
155
- assert_equal caller_line[ActiveModel::Serializer::CALLER_FILE], path
156
- end
157
-
158
- def test_serializer_file_path_on_windows
159
- path = 'c:/git/emberjs/ember-crm-backend/app/serializers/lead_serializer.rb'
160
- caller_line = "#{path}:1:in `<top (required)>'"
161
- assert_equal caller_line[ActiveModel::Serializer::CALLER_FILE], path
162
- end
163
-
164
- def test_serializer_file_path_with_space
165
- path = '/Users/git/ember js/ember-crm-backend/app/serializers/lead_serializer.rb'
166
- caller_line = "#{path}:1:in `<top (required)>'"
167
- assert_equal caller_line[ActiveModel::Serializer::CALLER_FILE], path
168
- end
169
-
170
- def test_serializer_file_path_with_submatch
171
- # The submatch in the path ensures we're using a correctly greedy regexp.
172
- path = '/Users/git/ember js/ember:123:in x/app/serializers/lead_serializer.rb'
173
- caller_line = "#{path}:1:in `<top (required)>'"
174
- assert_equal caller_line[ActiveModel::Serializer::CALLER_FILE], path
175
- end
176
-
177
- def test_digest_caller_file
178
- contents = "puts 'AMS rocks'!"
179
- dir = Dir.mktmpdir('space char')
180
- file = Tempfile.new('some_ruby.rb', dir)
181
- file.write(contents)
182
- path = file.path
183
- caller_line = "#{path}:1:in `<top (required)>'"
184
- file.close
185
- assert_equal ActiveModel::Serializer.digest_caller_file(caller_line), Digest::MD5.hexdigest(contents)
186
- ensure
187
- file.unlink
188
- FileUtils.remove_entry dir
189
- end
190
-
191
- def test_warn_on_serializer_not_defined_in_file
192
- called = false
193
- serializer = Class.new(ActiveModel::Serializer)
194
- assert_match(/_cache_digest/, (capture(:stderr) do
195
- serializer.digest_caller_file('')
196
- called = true
197
- end))
198
- assert called
199
- end
200
-
201
- private
202
-
203
- def render_object_with_cache(obj)
204
- ActiveModel::SerializableResource.new(obj).serializable_hash
205
- end
206
- end
207
- end
208
- end
209
-